You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

AngularJS两个Service的self互相覆盖问题技术问询

问题原因分析与解决方案

嘿,这是一个典型的JavaScript作用域陷阱问题!你的两个服务里都直接使用了未声明的self变量,导致它们共享了同一个全局对象,这就是为什么断点时第二个服务的self会被第一个服务的内容填充。

问题本质

在JavaScript中,如果一个变量没有用var/let/const声明,它会被自动提升到全局作用域(浏览器环境下就是window.self)。你的两个服务都在给同一个全局self对象的Model属性赋值,所以第二个服务的self.Model会和第一个服务的Model共享同一个对象,最终两个服务共用同一个self实例。

修复方案

每个服务内部需要声明自己的局部self变量,指向当前服务的单例实例(AngularJS的service基于构造函数模式,this默认指向服务的单例对象)。

修改后的第一个服务代码

(function () { 
    'use strict'; 
    angular.module('IPortal.Angular.Components.List.Shared.List.Factory', []) 
    .service('listfactory', ['$http', 'loggingService', 'listApiLink', 'listFormRenderService', 'listGridRenderService', 
        function ($http, loggingService, listApiLink, listFormRenderService, listGridRenderService) { 
            // 声明局部self,绑定当前服务实例
            var self = this;
            
            self.Model = { 
                IsLoadingGrid: false, 
                IsLoadingForm: false, 
                TotalColumns: 0, 
                TotalRows: 0, 
                List:[], 
                ListGrid: [], 
                ListForm: [], 
                ListFormTemplateURL: '', 
                ListGridTemplateURL: '', 
                BaseDate: new Date(), 
                PendingUpdates : [], 
            }; 

            // 注意:原代码递归调用自身会导致无限循环,需替换为实际业务逻辑
            self.GetListbyId = function (id, listType) { 
                // 示例:发起HTTP请求获取数据
                // return $http.get(`${listApiLink}/lists/${id}?type=${listType}`)
                //     .then(res => {
                //         self.Model.List = res.data;
                //         return self.Model;
                //     });
            };

            self.GetListDetailbyId = function (id, listType) { 
                // 同理,添加实际的详情获取逻辑
            };

            self.SaveAnswer = function (pendingQuestion) { 
                var pendingAdd = true; 
                if (self.Model.PendingUpdates.length > 0) { 
                    self.Model.PendingUpdates = self.Model.PendingUpdates.filter(function (pendingValue) { 
                        if (pendingValue.id === pendingQuestion.id) { 
                            pendingAdd = true; 
                            return false; 
                        } 
                        return true; 
                    }); 
                } 
                if (pendingAdd) { 
                    self.Model.PendingUpdates.push(pendingQuestion); 
                } 
            }; 

            self.Save = function () { 
                var pendingData = self.Model.PendingUpdates; 
                // 添加实际的保存逻辑,比如提交HTTP请求
            }; 

            // 暴露服务的公共方法和属性
            return { 
                GetListbyId: self.GetListbyId, 
                GetListDetailbyId: self.GetListDetailbyId, 
                SaveAnswer: self.SaveAnswer, 
                Save: self.Save,
                Model: self.Model
            }; 
        }]); 
})();

修改后的第二个服务代码

(function () { 
    'use strict'; 
    // 注意:RenderForm依赖listFormRenderService,需添加到服务依赖中
    angular.module('IPortal.Angular.Components.List.ListForm.InputDirectives.ClinicalOrderStatus.factory', []) 
    .service('clinicalorderstatusfactory', ['$http', 'loggingService', 'listFormRenderService', 
        function ($http, loggingService, listFormRenderService) { 
            var self = this;
            
            self.Model = { 
                primaryKey: 0, 
                status : '', 
                statusCode : '', 
                ListFormTemplateURL: '',
                FormTemplateIsRendered: false
            }; 

            // 修正原代码拼写错误:UpdataStatus → UpdateStatus
            self.UpdateStatus = function (primaryKey, patientId, status, reason, accountId) { 
                // 添加实际的更新状态逻辑,比如提交HTTP请求
            }; 

            self.RenderForm = function () { 
                self.Model.ListFormTemplateURL = listFormRenderService.Render(self.Model.ListForm); 
                self.Model.FormTemplateIsRendered = true; 
            }; 

            return { 
                UpdateStatus: self.UpdateStatus, 
                Data: self.Model, 
                RenderForm: self.RenderForm
            }; 
        }]); 
})();

额外注意事项

  • 拼写错误修正:原第二个服务里的UpdataStatus是拼写错误,改为UpdateStatus后才能正常调用。
  • 依赖注入:第二个服务的RenderForm方法使用了listFormRenderService,必须将其添加到服务的依赖数组中,否则会抛出“undefined”错误。
  • 避免无限递归:第一个服务的GetListbyId原代码递归调用自身,会导致无限循环,必须替换为实际的业务逻辑(比如发起HTTP请求)。

内容的提问来源于stack exchange,提问作者Simon

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.12 04:38:48