Using Upload() in Grid with GridEditMode.PopUp

3 posts, 0 answers
  1. Phillip
    Phillip avatar
    9 posts
    Member since:
    May 2018

    Posted 03 Aug 2018 Link to this post

    I've been searching and and I cannot find a thread or answer for what I'm doing specifically. I have a site where a user will be creating a record called 'ManualProcess'. In the pop-up they will enter general information about the record and then with the Upload() select files to be uploaded and associated to this main record. The files will be stored in a separate table name 'ManualPrcoessDeocuments' with a FK relationship back to the 'ManualProcess' record.

     

    What I'm trying to do is have the HttpPostedFileBase[] object be passed back to the controller along with the 'ManualProcess' record. I have been able to get it to call and pass a value using the async option but that occurs before they have sent the main record data. So ido not have the main record id to associate the documents with. 

    Below is the grid code.

    @(Html.Kendo().Grid(Model).Name("ManualWorkflowProcess").Columns(c =>
          {
              c.Bound(e => e.Name);
              c.Bound(e => e.Description);
              c.Bound(e => e.ApprovalProcessName);
              c.Bound(e => e.Active).ClientTemplate("<input type='checkbox' disabled='disabled' value='#= Active #' " + "# if (Active) { #" + "checked='Active'" + "# } #" + "/>").Width(100);
              c.Command(command =>
              {
                  command.Edit();
                  command.Destroy();
              }).Width(200);
          })
              .ToolBar(toolbar => toolbar.Create().Text("Create New Process"))
              .Editable(editable => editable.Mode(GridEditMode.PopUp).TemplateName("ManualProcessPopUp").Window(w => w.Width(700)))
              .Pageable(pager => pager.AlwaysVisible(false).PageSizes(new List<object> { 5, 10, 20, 100 }))
              .Sortable()
              .Filterable()
              .Groupable()
              .Events(events => events.Edit("Edit"))
              .DataSource(dataSource => dataSource
                      .Ajax()
                      .PageSize(20)
                      .Model(model => model.Id(p => p.Id))
                      .Create(update => update.Action("EditingPopup_Create", "ManualApprovalProcesses"))
                      .Read(read => read.Action("EditingPopup_Read", "ManualApprovalProcesses"))
                      .Update(update => update.Action("EditingPopup_Update", "ManualApprovalProcesses"))
                  .Destroy(update => update.Action("EditingPopup_Destroy", "ManualApprovalProcesses"))
            ))

     

    Below is the Upload() code in the pop-up template

    <div class="editor-label">
        @Html.Label("Files", htmlAttributes: new { @class = "control-label col-md-10" })
    </div>
    <div class="editor-field">
        @(Html.Kendo().Upload().Name("FileUploads").HtmlAttributes(new { aria_label = "files" })))
    </div>

    Below is my controller code.

    [AcceptVerbs(HttpVerbs.Post)]
            public ActionResult EditingPopup_Update([DataSourceRequest] DataSourceRequest request, ManualApprovalProcess manualProcess, HttpPostedFileBase[] fileUploads)
            {
                if (manualProcess != null && ModelState.IsValid)
                {
                    this.Update(manualProcess);
                }
     
                return Json(new[] { manualProcess }.ToDataSourceResult(request, ModelState));
            }

     

    So I want to have the file data passed back to the controller so I can create the main record and then use that id and loop over the documents and use that new id when creating the document records.

    If this possible the way I'm trying to achieve this? I can;t do the async call because I will be missing come data that I need to properly upload and create the document records as well as upload them to the correct location in Azure.

     

     

     

  2. Veselin Tsvetanov
    Admin
    Veselin Tsvetanov avatar
    994 posts

    Posted 07 Aug 2018 Link to this post

    Hello Phillip,

    I am afraid, that sending the file(s) along the Drid item data in the same request to the server would not be possible in this case. The reason for that is the fact that the files are submitted with a FormData ​request, while the Grid submits a regular XHR request.

    Having that said, here is what I would suggest you in this scenario:

    - Use an upload widget in AsyncMode with its AutoUpload() option set to false. In this way the files would not be automatically uploaded upon user selection.

    - Prevent the default behaviour of the edit form to submit the edited / created Grid item on the Edit button click. Instead, call the Upload() method of the Upload widget to sent the files to the server.

    - Save the files to a temporary location on Azure and as database entries. Return to the client the IDs of the uploaded files as a JSON response (it is important to be a JSON, so the widget knows that the upload process was successful).

    - Implement an event handler for the Upload success event. In that event retrieve the uploaded files IDs and store them in a hidden field on the edit form. Do not forget to trigger change on the hidden input:
    $('#test').val(e.response.ids).trigger("change");

    - Submit the Grid item to the Create / Update controller by calling the Grid.saveRow() method. The hidden field name should correspond to a property in the Grid Item model class. In this way the IDs of the files sent to the server will be available in the Grid model.

    - On the server, after the new Grid item has been created in the database table, retrieve its ID. Then you can set it as a foreign key for the items in the files database table, which have IDs corresponding to those sent in the hidden field. At this point you should be able to also save the files to their proper final location on Azure.

    Regards,
    Veselin Tsvetanov
    Progress Telerik
    Get quickly onboarded and successful with your Telerik and/or Kendo UI products with the Virtual Classroom free technical training, available to all active customers. Learn More.
  3. Phillip
    Phillip avatar
    9 posts
    Member since:
    May 2018

    Posted 17 Aug 2018 Link to this post

    Thank you Veselin for the response. We decided to go a different route with this portion of the solution but I will try what you suggested as I want to still use the Upload() control within a pop-up window in another area of the project where I will know some of the data already.
Back to Top