はじめに
最後に、レコードの作成について説明する最も重要なレッスンの1つに進みます。 登録フォームに記入するときの複雑なものから、必要なときに簡単なものまで、サイト上のあらゆるアクションは、次のように発生します。
- サイトへのリクエストの取得\取得
 - 承認と認証
 - 入力されたデータの妥当性の検証(検証)
 - 入力されたデータの検証により、入力されたデータが正しくないことが示された場合、入力するフォームに警告が表示されます。
 - 入力されたデータの検証でこのデータが正しいことが示された場合、それらはデータベースに保存され、確認ページが表示されます。
 
登録
ユーザー登録フォームを作成しましょう。 登録するとき、ユーザーはキャプチャを認識し、パスワードを繰り返す必要があります。 しかし、それなしで始めましょう。 UserControllerおよびViewでRegisterメソッドを作成します。
public ActionResult Register() { var newUser = new User(); return View(newUser); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      
      新しいユーザーオブジェクトを作成し、ビューに渡します。 フィールドは2つしかないため、入力するビューを作成します。
 @using (Html.BeginForm("Register", "User", FormMethod.Post, new { @class = "form-horizontal" })) { <fieldset> <div class="control-group"> <label class="control-label" for="Email"> Email </label> <div class="controls"> @Html.ValidationMessage("Email") @Html.TextBox("Email", Model.Email) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Password </label> <div class="controls"> @Html.ValidationMessage("Password") @Html.Password("Password", Model.Password) </div> </div> <div class="form-actions"> <button type="submit" class="btn btn-primary"> Register </button> @Html.ActionLink("Cancel", "Index", null, null, new { @class = "btn" }) </div> </fieldset> }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      これらのすべてのdiv、フィールドセット、およびボタンは、 ブートストラップフレームワークで説明されているように、似たようなもので作成されます(さらに学習します)。
基本的なHTML挿入について学習しましょう。
 Html.BeginForm("Register", "User", FormMethod.Post, new { @class = "form-horizontal" })
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      -タグを作成し
     Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email) 
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password") 
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password) 
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 
     Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 
     Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper 
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope(); 
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 
     Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 -  
Dispose()
(using() {}
)
@Html.TextBox("Email", Model.Email)
-(.. Email )
@Html.ValidationMessage("Password")
-
@Html.Password("Password", Model.Password)
-
Register Http- POST ( FormMethod.Post
Email=&Password=.
Register, User, HttpPost, — HttpGet. , , :
[HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
Register , :
 
      
, Email Password , (default).
2 ( ), User partial class:
public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName"> 1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
, 1234.
:
email Email – , .. Email - 1234
- , .
IValidatableObject
User - partial, IValidatableObject , , , System.Component.DataAnnotation. , , – MVC. .
User:
public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { // Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult(" email", new string[] { "Email" }); } // if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } // if (Password != ConfirmPassword) { yield return new ValidationResult(" ", new string[] { "ConfirmPassword" }); } } }
4 6 , , .
, :
 
      
, .
: Html.ValidationMessage(“ErrorField”) Html.ValidationSummary(). , , — ( ) .
Email (/Areas/Default/UserController.cs:Register):
if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); }
:
 
      
, , , , :
User , , , , . .. , : , , . Model- Controller- – .
, , User, . UserView Models/ViewModels:
public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
Automapping
, , . , User, , - UserView User , . – , , Update[Table] . object-to-object.
, automapper ( http://automapper.org/ ). , , , , .
Automapper:
Install-Package AutoMapper
, + Ninject, .
/Mappers:
public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
:
public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
( -) (/App_Start/NinjectWebCommon.cs):
kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
BaseController (/Controllers/BaseController.cs):
public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
UserController ( View) UserView:
[HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", " "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", " email "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO: } return View(userView); }
Register.cshtml :
@model LessonProject.Models.ViewModels.UserView
UserView .
:
using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage=" ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
:
 
      
5 6 . , email – . -, email:
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
, , , «» . , « », .. – , . , , . , .
: DataAnnotationsExtensions, ( http://dataannotationsextensions.org/ )
. , , , .
. Birthdate datetime null.
: , , :
 
      
2012-1-1
Birthdate datetime not nullLessonProjectDb.dbml
User Server Explorer SqlRepository/User.cs UpdateUser():
public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
UserView Bithdate. .
:
 
      
. – . Html ( ) DropDownList, .
:
@Html.DropDownList(string name, IEnumerable selectList)
SelectListItem:
public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
, , 1 - apple, 2 – orange (), 3 - banana :
public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
DropDownList()
, – name, Value () .
C :
public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
View:
<div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
- point . , UserView:
 
      
 
      
User. (/Mappers/CommonMapper.cs):
Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
BirthdateDay, BirthdateMonth, BirthdateYear Birthdate .
Captcha
, , . . . , .
Tools/CaptchaImage.cs:/// <summary> /// /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
, Image , ( ) GenerateImage().
UserController.Captcha():
public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
:
1111 9999. ci CatchaImage header mime- http- “image/jpeg” .. jpeg. bitmap ImageFormat.Jpeg Bitmap null,
Register.cshtml (/Areas/Default/View/User/Register.cshtml):
<label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
(/Areas/Default/Controllers/UserController.cs):
if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", " "); }
, . , :
if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
https://bitbucket.org/chernikov/lessons
 
     Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
            Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
    
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
           Dispose()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     (  using() {}
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.TextBox("Email", Model.Email)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -    (..      Email  ) 
      
        
        
        
      
     
      
        
        
        
      
     @Html.ValidationMessage("Password")
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -       
      
        
        
        
      
     
      
        
        
        
      
     @Html.Password("Password", Model.Password)
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     -   
      
        
        
        
      
     
      
        
        
        
      
         Register  Http-  POST (  FormMethod.Post
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
        Email=&Password=. 
      
        
        
        
      
       Register,      User,     HttpPost,   —  HttpGet.  ,          ,  : 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUser = new User(); return View(newUser); } [HttpPost] public ActionResult Register(User user) { return View(user); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
           Register  ,     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,   Email  Password ,       (default). 
      
        
        
        
      
           2  (   ),       User partial class: 
      
        
        
        
      
     public partial class User { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        View: 
      
        
        
        
      
     <div class="control-group"> <label class="control-label" for="FirstName"> Confirm Password </label> <div class="controls"> @Html.ValidationMessage("ConfirmPassword") @Html.Password("ConfirmPassword", Model.ConfirmPassword) </div> </div> <div class="control-group"> <label class="control-label" for="FirstName"> Captcha </label> </div> <div class="control-group"> <label class="control-label" for="FirstName">   1234 </label> <div class="controls"> @Html.ValidationMessage("Captcha") @Html.TextBox("Captcha", Model.Captcha) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         ,     1234. 
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
        : 
      
        
        
        
      
      email   Email –     , ..   Email    -         1234 
      
        
        
        
      
     
      
        
        
        
      
      -     ,   . 
      
        
        
        
      
     
      
        
        
        
      
     IValidatableObject 
      
        
        
        
      
          User - partial,       IValidatableObject ,  , ,     System.Component.DataAnnotation.    ,       ,   –     MVC.       . 
      
        
        
        
      
      User: 
      
        
        
        
      
     public partial class User : IValidatableObject { public static string GetActivateUrl() { return Guid.NewGuid().ToString("N"); } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { //  Email if (string.IsNullOrWhiteSpace(Email)) { yield return new ValidationResult(" email", new string[] {"Email"}); } // Email var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(Email); if (!(match.Success && match.Length == Email.Length)) { yield return new ValidationResult("  email", new string[] { "Email" }); } //   if (string.IsNullOrWhiteSpace(Password)) { yield return new ValidationResult(" ", new string[] { "Password" }); } //  if (Password != ConfirmPassword) { yield return new ValidationResult("  ", new string[] { "ConfirmPassword" }); } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
         4  6  ,    ,      . 
      
        
        
        
      
      , : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     ,      . 
      
        
        
        
      
     
      
        
        
        
      
          :  Html.ValidationMessage(“ErrorField”)  Html.ValidationSummary().   ,     ,   —   (  ) . 
      
        
        
        
      
     
      
        
        
        
      
               Email   (/Areas/Default/UserController.cs:Register): 
      
        
        
        
      
     if (user.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, user.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
      ,    ,   ,   ,    : 
      
        
        
        
      
      User           , , ,      ,      . ..     ,   :  ,   ,   .      Model-    Controller- –    . 
      
        
        
        
      
     
      
        
        
        
      
       ,   ,     User,  .    UserView     Models/ViewModels: 
      
        
        
        
      
     public class UserView { public int ID { get; set; } public string Email { get; set; } public string Password { get; set; } public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     Automapping 
      
        
        
        
      
           ,  ,     .     ,        User,   ,   -        UserView  User ,   .        –  ,   ,        Update[Table]  .         object-to-object. 
      
        
        
        
      
        ,  automapper ( http://automapper.org/ ). ,            , ,    ,       . 
      
        
        
        
      
     
      
        
        
        
      
      Automapper: 
      
        
        
        
      
     Install-Package AutoMapper
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             ,    +      Ninject,      . 
      
        
        
        
      
       /Mappers: 
      
        
        
        
      
     
      
        
        
        
      
     public interface IMapper { object Map(object source, Type sourceType, Type destinationType); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     : 
      
        
        
        
      
     public class CommonMapper : IMapper { static CommonMapper() { Mapper.CreateMap<User, UserView>(); Mapper.CreateMap<UserView, User>(); } public object Map(object source, Type sourceType, Type destinationType) { return Mapper.Map(source, sourceType, destinationType); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (   -) (/App_Start/NinjectWebCommon.cs): 
      
        
        
        
      
     
      
        
        
        
      
     kernel.Bind<IMapper>().To<CommonMapper>().InSingletonScope();
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      BaseController (/Controllers/BaseController.cs): 
      
        
        
        
      
      public abstract class BaseController : Controller { [Inject] public IRepository Repository { get; set; } [Inject] public IMapper ModelMapper { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
       UserController ( View)   UserView: 
      
        
        
        
      
     [HttpGet] public ActionResult Register() { var newUserView = new UserView(); return View(newUserView); } [HttpPost] public ActionResult Register(UserView userView) { if (userView.Captcha != "1234") { ModelState.AddModelError("Captcha", "    "); } var anyUser = Repository.Users.Any(p => string.Compare(p.Email, userView.Email) == 0); if (anyUser) { ModelState.AddModelError("Email", "   email  "); } if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); //TODO:  } return View(userView); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       Register.cshtml   : 
      
        
        
        
      
     @model LessonProject.Models.ViewModels.UserView
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      
      
        
        
        
      
      UserView     . 
      
        
        
        
      
     
      
        
        
        
      
      : 
      
        
        
        
      
      using System.ComponentModel.DataAnnotations; public class UserView { public int ID { get; set; } [Required(ErrorMessage=" email")] public string Email { get; set; } [Required(ErrorMessage=" ")] public string Password { get; set; } [Compare("Password", ErrorMessage="  ")] public string ConfirmPassword { get; set; } public string Captcha { get; set; } public string AvatarPath { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         5  6  . ,    email – .     -,    email: 
      
        
        
        
      
      [AttributeUsage(AttributeTargets.Property, AllowMultiple = false)] public class ValidEmailAttribute : ValidationAttribute { public override bool IsValid(object value) { if (value == null) { return true; } if (!(value is string)) { return true; } var source = value as string; if (string.IsNullOrWhiteSpace(source)) { return true; } var regex = new Regex(@"\w+([-+.']\w+)*@\w+([-.]\w+)*\.\w+([-.]\w+)*", RegexOptions.Compiled); var match = regex.Match(source); return (match.Success && match.Length == source.Length); } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      ,     ,    ,    «»  .   ,  «     », ..       –   ,     .  ,    , .  ,               . 
      
        
        
        
      
     
      
        
        
        
      
     :   DataAnnotationsExtensions,       ( http://dataannotationsextensions.org/ ) 
      
        
        
        
      
     
      
        
        
        
      
         . ,  ,  ,     . 
      
        
        
        
      
     
      
        
        
        
      
        . Birthdate datetime null. 
      
        
        
        
      
     : ,     ,     : 
      
        
        
        
      
     
 
      
        
        
        
      
           2012-1-1 
      
        
        
        
      
       Birthdate  datetime not null   LessonProjectDb.dbml
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      User     Server Explorer  SqlRepository/User.cs    UpdateUser(): 
      
        
        
        
      
     public bool UpdateUser(User instance) { User cache = Db.Users.Where(p => p.ID == instance.ID).FirstOrDefault(); if (cache != null) { cache.Birthdate = instance.Birthdate; cache.AvatarPath = instance.AvatarPath; cache.Email = instance.Email; Db.Users.Context.SubmitChanges(); return true; } return false; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      UserView         Bithdate.      . 
      
        
        
        
      
     
      
        
        
        
      
           : 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
         .    –     .  Html (     )  DropDownList,    . 
      
        
        
        
      
      : 
      
        
        
        
      
     @Html.DropDownList(string name, IEnumerable selectList) 
      
        
        
        
      
     
      
        
        
        
      
      SelectListItem: 
      
        
        
        
      
     public class SelectListItem { public SelectListItem(); public bool Selected { get; set; } public string Text { get; set; } public string Value { get; set; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
      , ,  1 - apple, 2 – orange (), 3 - banana     : 
      
        
        
        
      
     public IEnumerable<SelectListItem> SelectFruit { get { yield return new SelectListItem() { Value = "1", Text = "apple", Selected = false }; yield return new SelectListItem() { Value = "2", Text = "orange", Selected = true }; yield return new SelectListItem() { Value = "3", Text = "banana", Selected = false }; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
        DropDownList()
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
      ,   – name,    Value   () . 
      
        
        
        
      
     C     : 
      
        
        
        
      
     
      
        
        
        
      
     public int BirthdateDay { get; set; } public int BirthdateMonth { get; set; } public int BirthdateYear { get; set; } public IEnumerable<SelectListItem> BirthdateDaySelectList { get { for (int i = 1; i < 32; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateDay == i }; } } } public IEnumerable<SelectListItem> BirthdateMonthSelectList { get { for (int i = 1; i < 13; i++) { yield return new SelectListItem { Value = i.ToString(), Text = new DateTime(2000, i, 1).ToString("MMMM"), Selected = BirthdateMonth == i }; } } } public IEnumerable<SelectListItem> BirthdateYearSelectList { get { for (int i = 1910; i < DateTime.Now.Year; i++) { yield return new SelectListItem { Value = i.ToString(), Text = i.ToString(), Selected = BirthdateYear == i }; } } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       View: 
      
        
        
        
      
      <div class="control-group"> <label class="control-label" for="FirstName"> Birth date </label> <div class="controls"> @Html.DropDownList("BirthdateDay", Model.BirthdateDaySelectList) @Html.DropDownList("BirthdateMonth", Model.BirthdateMonthSelectList) @Html.DropDownList("BirthdateYear", Model.BirthdateYearSelectList) </div> </div>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
         - point   . ,           UserView: 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
     
 
      
        
        
        
      
     
      
        
        
        
      
            User.       (/Mappers/CommonMapper.cs): 
      
        
        
        
      
      Mapper.CreateMap<User, UserView>() .ForMember(dest => dest.BirthdateDay, opt => opt.MapFrom(src => src.Birthdate.Day)) .ForMember(dest => dest.BirthdateMonth, opt => opt.MapFrom(src => src.Birthdate.Month)) .ForMember(dest => dest.BirthdateYear, opt => opt.MapFrom(src =>src.Birthdate.Year)); Mapper.CreateMap<UserView, User>() .ForMember(dest => dest.Birthdate, opt => opt.MapFrom(src => new DateTime(src.BirthdateYear, src.BirthdateMonth, src.BirthdateDay)));
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
             BirthdateDay, BirthdateMonth, BirthdateYear  Birthdate  . 
      
        
        
        
      
     
      
        
        
        
      
     Captcha 
      
        
        
        
      
       ,    ,          .       .      .    ,     . 
      
        
        
        
      
      Tools/CaptchaImage.cs: /// <summary> ///   /// </summary> public class CaptchaImage { public const string CaptchaValueKey = "CaptchaImageText"; public string Text { get { return text; } } public Bitmap Image { get { return image; } } public int Width { get { return width; } } public int Height { get { return height; } } // Internal properties. private string text; private int width; private int height; private string familyName; private Bitmap image; // For generating random numbers. private Random random = new Random(); public CaptchaImage(string s, int width, int height) { text = s; SetDimensions(width, height); GenerateImage(); } public CaptchaImage(string s, int width, int height, string familyName) { text = s; SetDimensions(width, height); SetFamilyName(familyName); GenerateImage(); } // ==================================================================== // This member overrides Object.Finalize. // ==================================================================== ~CaptchaImage() { Dispose(false); } // ==================================================================== // Releases all resources used by this object. // ==================================================================== public void Dispose() { GC.SuppressFinalize(this); Dispose(true); } // ==================================================================== // Custom Dispose method to clean up unmanaged resources. // ==================================================================== protected virtual void Dispose(bool disposing) { if (disposing) // Dispose of the bitmap. image.Dispose(); } // ==================================================================== // Sets the image aWidth and aHeight. // ==================================================================== private void SetDimensions(int aWidth, int aHeight) { // Check the aWidth and aHeight. if (aWidth <= 0) throw new ArgumentOutOfRangeException("aWidth", aWidth, "Argument out of range, must be greater than zero."); if (aHeight <= 0) throw new ArgumentOutOfRangeException("aHeight", aHeight, "Argument out of range, must be greater than zero."); width = aWidth; height = aHeight; } // ==================================================================== // Sets the font used for the image text. // ==================================================================== private void SetFamilyName(string aFamilyName) { // If the named font is not installed, default to a system font. try { Font font = new Font(aFamilyName, 12F); familyName = aFamilyName; font.Dispose(); } catch (Exception) { familyName = FontFamily.GenericSerif.Name; } } // ==================================================================== // Creates the bitmap image. // ==================================================================== private void GenerateImage() { // Create a new 32-bit bitmap image. Bitmap bitmap = new Bitmap(width, height, PixelFormat.Format32bppArgb); // Create a graphics object for drawing. Graphics g = Graphics.FromImage(bitmap); g.SmoothingMode = SmoothingMode.AntiAlias; Rectangle rect = new Rectangle(0, 0, width, height); // Fill in the background. HatchBrush hatchBrush = new HatchBrush(HatchStyle.SmallConfetti, Color.LightGray, Color.White); g.FillRectangle(hatchBrush, rect); // Set up the text font. SizeF size; float fontSize = rect.Height + 1; Font font; // Adjust the font size until the text fits within the image. do { fontSize--; font = new Font(familyName, fontSize, FontStyle.Bold); size = g.MeasureString(text, font); } while (size.Width > rect.Width); // Set up the text format. StringFormat format = new StringFormat(); format.Alignment = StringAlignment.Center; format.LineAlignment = StringAlignment.Center; // Create a path using the text and warp it randomly. GraphicsPath path = new GraphicsPath(); path.AddString(text, font.FontFamily, (int)font.Style, font.Size, rect, format); float v = 4F; PointF[] points = { new PointF(random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, random.Next(rect.Height) / v), new PointF(random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v), new PointF(rect.Width - random.Next(rect.Width) / v, rect.Height - random.Next(rect.Height) / v) }; Matrix matrix = new Matrix(); matrix.Translate(0F, 0F); path.Warp(points, rect, matrix, WarpMode.Perspective, 0F); // Draw the text. hatchBrush = new HatchBrush(HatchStyle.LargeConfetti, Color.LightGray, Color.DarkGray); g.FillPath(hatchBrush, path); // Add some random noise. int m = Math.Max(rect.Width, rect.Height); for (int i = 0; i < (int)(rect.Width * rect.Height / 30F); i++) { int x = random.Next(rect.Width); int y = random.Next(rect.Height); int w = random.Next(m / 50); int h = random.Next(m / 50); g.FillEllipse(hatchBrush, x, y, w, h); } // Clean up. font.Dispose(); hatchBrush.Dispose(); g.Dispose(); // Set the image. image = bitmap; } }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
     
      
        
        
        
      
      ,    Image  ,    (    )  GenerateImage(). 
      
        
        
        
      
     
      
        
        
        
      
         UserController.Captcha(): 
      
        
        
        
      
     public ActionResult Captcha() { Session[CaptchaImage.CaptchaValueKey] = new Random(DateTime.Now.Millisecond).Next(1111, 9999).ToString(); var ci = new CaptchaImage(Session[CaptchaImage.CaptchaValueKey].ToString(), 211, 50, "Arial"); // Change the response headers to output a JPEG image. this.Response.Clear(); this.Response.ContentType = "image/jpeg"; // Write the image to the response stream in JPEG format. ci.Image.Save(this.Response.OutputStream, ImageFormat.Jpeg); // Dispose of the CAPTCHA image object. ci.Dispose(); return null; }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       : 
      
        
        
        
      
           1111  9999.   ci  CatchaImage     header  mime-  http-  “image/jpeg” ..   jpeg.  bitmap      ImageFormat.Jpeg   Bitmap  null,          
      
        
        
        
      
     
      
        
        
        
      
        Register.cshtml (/Areas/Default/View/User/Register.cshtml): 
      
        
        
        
      
     <label class="control-label" for="FirstName"> <img src="@Url.Action("Captcha", "User")" alt="captcha" /> </label>
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
      (/Areas/Default/Controllers/UserController.cs): 
      
        
        
        
      
     if (userView.Captcha != (string)Session[CaptchaImage.CaptchaValueKey]) { ModelState.AddModelError("Captcha", "    "); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
       , .     ,   : 
      
        
        
        
      
     if (ModelState.IsValid) { var user = (User)ModelMapper.Map(userView, typeof(UserView), typeof(User)); Repository.CreateUser(user); return RedirectToAction("Index"); }
      
      
        
        
        
      
    
        
        
        
      
      
        
        
        
      
    
     
      
        
        
        
      
     
      
        
        
        
      
          https://bitbucket.org/chernikov/lessons