Нокаут. Js страница зависает после периодического возврата данных - PullRequest
0 голосов
/ 04 августа 2020

Итак, у меня есть аккордеон, который возвращает данные при нажатии кнопки ..

Вызов нокаута работает должным образом, но иногда страница просто зависает при возврате данных .. Я буквально все перепробовал и не могу понять, почему это могло произойти, поскольку я удаляю массив каждый раз перед вызовом ... Есть идеи?

HTML говорит, что ошибок нет, а также javascript в инструменты google dev ...

HTML

<section id="results" style="margin-top: 1em;">
  
        <div id="accordion">
            <div class="card">
                 <div class="card-header" id="headingOne">

        <table class="table table-striped table-hover">
            <thead>
                <tr>
                    <th>Set Next</th>
                    <th>Name</th>
                    <th>Bench</th>
                    <th>Transacted</th>
                    @*<th>Receipe Name</th>*@
                </tr>
            </thead>
            
            <tbody data-bind="foreach: Stages">

                <tr >
                    <td data-bind="css: CellClass">
                        <button class="btn btn-warning" data-bind="attr: {'data-id': Id}" onclick="saveStepId(this);" data-toggle="modal" data-target="#moveReason">@Html.LocalisedStringFor(model => model.MoveToStageText)</button>
                        <a class="text" data-bind="attr: {'data-id': Id}" data-toggle="modal"><span>@Html.LocalisedStringFor(model => model.CurrentPositionText)</span></a>
                    </td>

                    <td class="accordion-toggle" data-toggle="collapse" aria-expanded="false" data-bind="attr: {'data-target': '#' + RecipeName(), 'aria-controls': '#' + RecipeName()}, click: $root.GetRecipeHeader.bind(this, RecipeName())">
                        <!-- ko if: IsNext()-->
                        <svg width="1em" data-bind="if: RecipeName" height="1em" viewBox="0 0 16 16" class="bi bi-chevron-down" fill="currentColor" xmlns="http://www.w3.org/2000/svg">
                            <path fill-rule="evenodd" d="M1.646 4.646a.5.5 0 0 1 .708 0L8 10.293l5.646-5.647a.5.5 0 0 1 .708.708l-6 6a.5.5 0 0 1-.708 0l-6-6a.5.5 0 0 1 0-.708z" />
                        </svg>
                        <!--/ko-->
                        <!-- ko if: IsNext() === 'False'-->
                        &nbsp;&nbsp;&nbsp;
                         <!--/ko-->
                        <span data-bind="text: ProcessName"></span>
                    </td>
                    <td><span data-bind="text: BenchName"></span></td>
                    <td><span data-bind="text: TransactionStatus"></span></td>
                   
                </tr>
              
            <!-- ko if: IsNext() -->
                <tr id="" class="collapse" data-bind="attr: {'id':RecipeName}" data-parent="#accordion">
                   
                    <td colspan="5">
                        <div class="accordion-inner" >
                            <ul data-bind="foreach: $parent.RecipeStages">
                              
                                <li>
                                    <!--ko if: CanMove()-->
                                    <button class="btn btn-warning moveRecipeStep" onclick="saveRecipeId(this);" id="blah" data-bind="attr: {'data-id': StepId, data_recipe_name: $parent.RecipeName}" data-toggle="modal" data-target="#moveRecipeReason">@Html.LocalisedStringFor(model => model.MoveToStageText)</button>
                                    <svg width="2em" height="2em" viewBox="0 0 16 16" class="bi bi-arrow-left-short" fill="currentColor" xmlns="http://www.w3.org/2000/svg">
                                        <path fill-rule="evenodd" d="M7.854 4.646a.5.5 0 0 1 0 .708L5.207 8l2.647 2.646a.5.5 0 0 1-.708.708l-3-3a.5.5 0 0 1 0-.708l3-3a.5.5 0 0 1 .708 0z" />
                                        <path fill-rule="evenodd" d="M4.5 8a.5.5 0 0 1 .5-.5h6.5a.5.5 0 0 1 0 1H5a.5.5 0 0 1-.5-.5z" />
                                    </svg>
                                    <!--/ko--> &nbsp;
                                    <span data-bind="text: StepName"></span>
                                </li>
                            
                                
                            </ul>

                        </div>

                    </td>
                    
                </tr>
              <!--/ko-->
            </tbody>

        </table>
            </div>
    </div>
        </div>
      
</section>

Modals

<section id="hidden">
    <div class="modal fade" id="moveReason" tabindex="-1" role="dialog" arial-labelledby="moveReasonLabel" aria-hidden="true">
        <div class="modal-dialog" role="document">
            <div class="modal-content">
                <div class="modal-header">
                    <h5 class="modal-title" id="moveReasonLabel">What is the reason for the Step move?</h5>
                    <button type="button" class="close" data-dismiss="modal" aria-label="Close">
                        <span aria-hidden="true">&times;</span>
                    </button>
                </div>
                <div class="modal-body reasonDialog">
                    <form>
                        <div class="form-group">
                            @Html.LabelFor(model => model.ReasonText)
                            @Html.TextAreaFor(model => model.ReasonText, new { rows = 4, @class = "form-control", maxlength = "100", data_bind = "value: Reason" })
                        </div>
                    </form>
                </div>
                <div class="modal-footer">
                    <button id="DoMove" type="button" class="btn btn-primary">@Html.LocalisedStringFor(model => model.SubmitText)</button>
                </div>
            </div>
        </div>
    </div>
    <div class="modal fade" id="moveRecipeReason" tabindex="-1" role="dialog" arial-labelledby="moveReasonLabel" aria-hidden="true">
        <div class="modal-dialog" role="document">
            <div class="modal-content">
                <div class="modal-header">
                    <h5 class="modal-title" id="moveReasonLabel">What is the reason for the Recipe move?</h5>
                    <button type="button" class="close" data-dismiss="modal" aria-label="Close">
                        <span aria-hidden="true">&times;</span>
                    </button>
                </div>
                <div class="modal-body reasonDialog">
                    <form>
                        <div class="form-group">
                            @Html.LabelFor(model => model.ReasonText)
                            @Html.TextAreaFor(model => model.ReasonText, new { rows = 4, @class = "form-control", maxlength = "100", data_bind = "value: Reason" , id = "blah" })
                        </div>
                    </form>
                </div>
                <div class="modal-footer">
                    <button id="DoMoveRecipe" type="button" class="btn btn-primary">@Html.LocalisedStringFor(model => model.SubmitText)</button>
                </div>
            </div>
        </div>
    </div>
</section>

knockout.ks

 self.GetRecipeHeader = function(sRecipeName) {
                    self.RecipeStages.removeAll();
                    var sSerialNumber = self.SerialNumber().trim();
                    
                    

                    var newUrl =
                        '@Html.Raw(Url.Action("GetRecipeData", new {serialNumber = "SERIALNUMBER", recipeId = "RECIPEID", userLevel = 0}))'
                            .replace("SERIALNUMBER", sSerialNumber).replace("RECIPEID", sRecipeName);
                    $.getJSON(newUrl).done(function (returnData) {
                       
                        for (var stagepos = 0; stagepos < self.Stages().length; stagepos++) {
                            
                            var stage = self.Stages()[stagepos];
                            //alert("RecipeName =" + stage.RecipeName() + "And sRecpeName =" + sRecipeName
                            //    );
                            if (stage.RecipeName() === sRecipeName && stage.RecipeStages().length === 0) {
                                //alert("blah de blah");
                                if (returnData !== null && returnData.RecipeStages !== null) {
                                   
                                    for (var recipepos = 0; recipepos < returnData.RecipeStages.length; recipepos++) {
                                     
                                        self.RecipeStages.push(new recipeStepDetail(returnData.RecipeStages[recipepos].StepId,
                                            returnData.RecipeStages[recipepos].StepName, returnData.RecipeStages[recipepos].CanMove
                                        ));
                                        
                                    }
                                }
                                
                            }
                        }


                    }) .fail(function (xhr, status) { alert(status); });

                };
            };

, а также другой функция

 $("#DoMove, #DoMoveRecipe").click(function (e) {
                    
                    var input = $(this);
                    var buttonId = input.attr("id");
                    var id = input.data("id");
                   var url = buttonId === 'DoMove' ? '@Url.Action("MakeNext")' : '@Url.Action("MoveRecipePosition")';

                    //$("#moveReason").modal("toggle");
                    if (buttonId === "DoMove") {
                        $.ajax(url,
                            {
                                data: {
                                    "Id": stepId,
                                    "Reason": $("#moveReason .reasonDialog textarea").val(),
                                },
                                cache: false,
                                method: "POST",
                            }).done(function (returnData) {
                                $("#moveReason").modal('hide');
                                self.Stages.removeAll();
                                self.GetData(self.SerialNumber);
                            //if (returnData) {
                            //    if (returnData.BrokenRule !== null) {
                            //        alert(returnData.BrokenRule.Message);
                            //    } else if (returnData.ProcessStep !== null) {
                            //        var bFound = false;
                            //        //Done like this because you can only move backwards. Originally the logic was fuller but, most things don't change now.
                            //        //The extra logic just hides everything past the active one
                            //        for (var pos = 0; pos < viewModel.Stages().length; pos++) {
                            //            if (bFound) {
                            //                viewModel.Stages()[pos].Id(-1);
                            //                viewModel.Stages()[pos].IsNext(false);
                            //            } else if (viewModel.Stages()[pos].Id() == returnData.ProcessStep.Id) {
                            //                viewModel.Stages()[pos].IsNext(returnData.ProcessStep.IsNext);
                            //                viewModel.Stages()[pos].BenchId(returnData.ProcessStep.BenchId);
                            //                viewModel.Stages()[pos].BenchName(returnData.ProcessStep.BenchName);
                            //                viewModel.Stages()[pos].IsTransacted(returnData.ProcessStep.IsTransacted);
                            //                viewModel.Stages()[pos].RecipeName(returnData.ProcessStep.RecipeName);

                            //                bFound = true;
                            //            }
                            //        }
                            //    }
                            //}
                        }).fail(function(xhr) {
                            try {
                                console.log(xhr.statusText);
                                console.log(xhr.responseText);
                                alert(xhr.statusText + "\r\n" + xhr.responseText);
                            } catch (ex) {
                                console.log(ex);
                                alert(ex);
                            }
                        });
                    } else {
                        self.RecipeStages.removeAll();
                        $.ajax(url,
                            {
                                data: {
                                    "SerialNumber": viewModel.SerialNumber(),
                                    "Message": $("#moveRecipeReason .reasonDialog textarea").val(),
                                    "StepId": recipeStepId
                                },
                                cache: false,
                                method: "POST"
                            }).done(function (returnData) {
                                $("#moveRecipeReason").modal('hide');

                                self.GetRecipeHeader(recipeName);
                            
                                
                               // for (var pos = 0; pos < viewModel.RecipeStages().length; pos++) {
                                   
                                    //if (viewModel.RecipeStages()[pos].RecipeName && viewModel.RecipeStages()[pos].RecipeName == recipeName) {
                                    //alert(recipeName);
                                        
                                    //}
                                //}
                              
                            if (returnData) {
                                if (returnData.BrokenRule !== null) {
                                    alert(returnData.BrokenRule.Message);
                                } else if (returnData.recipePosition !== null) {
                                    var bFound = false;
                                    //Done like this because you can only move backwards. Originally the logic was fuller but, most things don't change now.
                                    //The extra logic just hides everything past the active one
                                    for (var pos = 0; pos < viewModel.Stages().length; pos++) {
                                        //if (viewModel.Stages()[pos].RecipeName() !==
                                        //    returnData.recipePosition.RecipeName)
                                        //    continue;

                                        for (var innerPos = 0;
                                            innerPos < viewModel.Stages()[pos].RecipeStages().length;
                                            innerPos++) {

                                            var recipeStage = viewModel.Stages()[pos].RecipeStages()[innerPos];
                                            
                                            if (bFound) {
                                                recipeStage.StepId(-1);
                                                recipeStage.IsNext(false);
                                            } else if (viewModel.Stages()[pos].Id() === returnData.ProcessStep.Id) {
                                                //recipeStage.StepId(-1);
                                                //recipeStage.IsNext(true);
                                                viewModel.Stages()[pos].RecipeName(returnData.ProcessStep.StepName,
                                                    returnData.ProcessStep.CanMove);

                                                bFound = true;
                                            }

                                        }
                                    }
                                }
                            }
                        }).fail(function(xhr) {
                            try {
                                console.log(xhr.statusText);
                                console.log(xhr.responseText);
                                alert(xhr.statusText + "\r\n" + xhr.responseText);
                            } catch (ex) {
                                console.log(ex);
                                alert(ex);
                            }
                        });
                    }
                })
            });
...