Category Archives: ASP.NET MVC

[ASP.NET MVC] The ForeignKeyAttribute on property is not valid


You might encounter the error (below) when working on ASP.NET MVC project stating that :

The ForeignKeyAttribute on property 'EmployeeId' on type 'EmployeeSalary' 
is not valid. The navigation property 'Employee' was not found on the dependent 
type 'EmployeeSalary'. The Name value should be a valid navigation property name.

This error occurred when you trying to set ForeignKey attribute without indicating navigate
property name.

Here our EmployeeSalary table :
public partial class EmployeeSalary 
 {
 [Key]
 public int id { get; set; }
 [ForeignKey("Employee")]
 public int EmployeeId { get; set; }
 public decimal Salary{ get; set; }
 }

As you might have already seen we didn’t assign navigate property name,therefore,the error above occurred.In order to solve this problem we should just add property as this:

public virtual Employee Employee { get; set; }

ASP.NET MVC Telerik Grid – file upload on popup mode


Supposing that you need to upload file(s) on popup mode of kendo grid.If your table has relationship with another table then you might want to assign id or whatsoever.
Firstly, let’s create our grid and some JavaScript codes.

@(Html.Kendo().Grid<ModelName>()
      .Name("grid")
      .Columns(columns =>
      {
        columns.Bound(c => c.ColumnName);
        columns.Bound(c => c.ColumnName2);
        // ...
        columns.Command(command => { command.Edit(); command.Destroy(); }).Width(180);
      })
      .ToolBar(toolbar => {
            toolbar.Create();
            toolbar.Excel();
      }) 

// AddContractDialog is our template for popup editing mode.
      .Editable(editable => editable.Mode(GridEditMode.PopUp).TemplateName("AddContractDialog"))
      .Scrollable()
      .DataSource(dataSource => dataSource
          .Ajax()
          .Model(model => model.Id(p => p.idSome))
          .Read(read => read.Action("Grid_Read", "ControllerName"))
              .Create(create => create.Action("Grid_Create", "ControllerName").Data("additionalDetail"))
          .Update(update => update.Action("Grid_Update", "ControllerName"))
          .Destroy(destroy => destroy.Action("Grid_Destroy", "ControllerName"))
      )
        )
<script>
    function additionalDetail() {
        return {
            filename: window.UploadedFile
        }
    }
</script>
<script>
   var UploadedFile;
    function onSuccess(e) {
        UploadedFile = e.response.fileName;
    }
</script>

What I did is add UploadedFile value that will pass the detail that comes from Success event of upload widget.By defining additionalDetail, we’ll pass our file name to grid’s create event.
Here is our kendo upload widget
(AddContractDialog.cshtml)

    @(Html.Kendo().Upload()
    .Name("attachments")
    .Async(async => async
        .Save("Save", "ControllerName")
    )
            .Events(c => c
                .Success("onSuccess")
            )
    )

For saving uploaded file and pass file name (in my case,you can pass whatever detail you want) to the Success event.

   public ActionResult Save(IEnumerable<HttpPostedFileBase> attachments)
        {
            string attachmentName = null;
           
            if (attachments != null)
            {
                foreach (var file in attachments)
                {
                    attachmentName = Path.GetFileName(file.FileName);
// Don't forget create CategoryImage folder.
                    var physicalPath = Path.Combine(Server.MapPath("~/CategoryImage/"), attachmentName );

                     file.SaveAs(physicalPath);
                }
            }

            // Return file name string to success event
          return Json(new { fileName = attachmentName }, "text/plain");
        }

and in Grid’s create event we add some extra parameter to get our file name.
Contract is just an example model

 
        [AcceptVerbs(HttpVerbs.Post)]
        public ActionResult Grid_Create([DataSourceRequest]DataSourceRequest request, Contract contract, string filename)
        {

Now you will receive your file’s name as parameter in the Grid_Create (as filename).

Resources:
http://docs.telerik.com/kendo-ui/aspnet-mvc/helpers/upload/metadata#receiving-metadata-from-the-save-handler
http://www.telerik.com/forums/grid-with-upload-in-custom-editor-template-popup#KXXGIwt6bUmZQHwFPjlojw

Load and Save ASP.NET MVC Settings


We have been using Settings both in WPF and WinForm.You might need to use Settings on your ASP.NET MVC application as well.Contrary to others, in MVC we should use web.config file to save and load our setting values.About security measures, if you are going to use web.config to save your password or other sensitive data,you need to encrypt them.

Firstly, we should add our value to the web.config file :

    <add key="returnEmployee" value="true">

to load our setting you should call OpenWebConfiguration method which is belongs WebConfigurationManager class.

 var mySetting = System.Web.Configuration.WebConfigurationManager.OpenWebConfiguration("~\\Views");
 var mySettingValue = mySetting.AppSettings.Settings["returnEmployee"].Value;

Keep in mind that “~\\Views” is a path of your web.config file.For saving your setting you just need to set some data to your setting and call Save() method as shown below.

  var mySetting = System.Web.Configuration.WebConfigurationManager.OpenWebConfiguration("~\\Views");
    mySetting.AppSettings.Settings["returnEmployee"].Value = "someValue";
    mySetting.Save();