【问题标题】:Angularjs / REST api - call api to display obj data based on another object in selectorAngularjs / REST api - 调用 api 以根据选择器中的另一个对象显示 obj 数据
【发布时间】:2016-03-16 19:37:19
【问题描述】:

我正在开发一个 SPA 网站,以显示我管理的垒球队的垒球统计数据。这个具体问题与使用 angularjs 显示 api 调用的结果有关,其中 api 调用基于选择器中选择的内容。

我正在使用的两个模型:

public class Team
{
    public int Id { get; set; }
    public string Name { get; set; }
    public string WeekNight { get; set; }
    public int? Year { get; set; }

    public int ManagerId { get; set; }
    public int LeagueId { get; set; }

    public virtual Manager Manager { get; set; }
    public virtual League League { get; set; }
    public virtual ICollection<Game> Games { get; set; }
    public virtual ICollection<Player> Players { get; set; }
    public virtual ICollection<Award> Awards { get; set; }
}

public class Award
{
    public int Id { get; set; }
    public int AwardTypeId { get; set; }
    public int PlayerId { get; set; }
    public int TeamId { get; set; }

    public virtual AwardType AwardType { get; set; }
    public virtual Player Player { get; set; }
    public virtual Team Team { get; set; }

}

在我的部分观点中,我有以下内容,它创建了一个选择器并将其填充到我的所有团队中:

var teamService = angular.module('teamService', ['ngResource']);

teamService.factory('Team', ['$resource',

  function($resource) {
    return $resource('api/v1/teams/:teamId', {}, {
      query: {
        method: 'GET',
        params: {
          teamId: '@teamId'
        },
        isArray: true
      },
      post: {
        method: 'POST'
      },
      update: {
        method: 'PUT',
        params: {
          teamId: '@teamId'
        }
      },
      remove: {
        method: 'DELETE'
      }
    });
  }
]);;


var teamController = angular.module('teamController', []);

teamController.controller('teamListController', ['$scope', 'Team',
  function($scope, Team) {
    $scope.teams = Team.query();
  }
]);
<div class="col-md-12">
  <div class="award-team-select col-md-offset-4 col-md-4">
    <select class="form-control" ng-controller="teamListController">
      <option ng-repeat="t in teams">{{t.year}} - {{t.name}} ({{t.weekNight}}'s)</option>
    </select>
  </div>
</div>

连接到我的 webAPI 这可以正常工作,并会返回类似:

2015 - SomeTeamName(星期一)

酷。现在,我想在下面显示该选定团队的奖项。我有一个这样创建的工作网址:

config.Routes.MapHttpRoute(
            name: "TeamAwards",
            routeTemplate: "api/v1/teams/{id}/awards/{awardId}",
            defaults: new { controller = "award", awardId = RouteParameter.Optional }
        );

使用 Google 的 Advanced Rest Cient,我可以获得特定团队的奖项……这就是我苦苦挣扎的地方。在选择器下方,我有一些格式精美的 div 来显示奖项。我想在选择器中显示团队的奖项。

我尝试向我的工厂添加另一个调用“api/v1/teams/{id}/awards/{awardId}”网址的函数,但我不确定如何从链接到新工厂的选择器中获取 teamId功能。然后我打算制作一个“teamAwardController”,它从工厂获取数据以显示在选择器下方的 div 中。

简而言之,我希望能够显示奖项,其中 Awards.teamId == 选择器中团队的 ID。

任何建议都会很棒。 谢谢!

添加编辑:

因此,根据当前的反馈,我也在尝试访问 TeamController 中的子奖项。所以如果我有:

 <div ng-controller="teamController">
   <div class="col-md-12">
     <div class="award-team-select col-md-offset-4 col-md-4">
       <select class="form-control">
         <option ng-repeat="t in teams">{{t.year}} - {{t.name}} ({{t.weekNight}}'s) </option>
       </select>
     </div>
   </div>

  <div class="col-md-4 col-sm-6 col-xs-12">
      // awards to go here
  </div>

</div>  // end teamController div

...我尝试在 teamController 中使用 ng-model="teams" ,然后在奖励部分使用 ng-bind="teams" 以及尝试 {{teams.awards}} 但没有骰子。我离这儿很远吗?

【问题讨论】:

  • 您是否考虑过简单地将奖项作为团队列表的一部分返回?看起来你的Team 模特儿时已经获得了奖项。
  • 我正在考虑这样做,但它必须在嵌套的 ng-repeat 中。我的问题是团队的 ng-repeat 位于一个已关闭的选择标签中,其父 div 也是如此。然后再往下,另一个 div 是我试图展示奖项的地方。
  • 所以基本上你需要一种方法来获取选定的团队 ID,将其传递到您的 teamAwardController 中,您将在其中调用您的 API 以获得团队的奖励。对吗?
  • 是的!因此下拉菜单使用调用 api/v1/teams/{id} 的 teamController。然后我会有一个调用 api/v1/teams/{teamId}/awards/{id} 的 teamAwardsController。但我不知道如何填充teamID。另外,我一直在尝试仅使用 TeamController 并通过子属性获得奖励,但我不确定如何获得它们。我仍然在包含 TeamController 的 div 下,我尝试使用 ng-model="teams" 然后在 Awards div 中使用 ng-bind,但没有运气。
  • 查看我在下面提供的答案 - 您可以维护单独的控制器模块。我不确定您在更新后的问题中尝试使用ng-modelng-bind 的位置或方式。

标签: angularjs asp.net-web-api


【解决方案1】:

您需要将&lt;select&gt; 绑定到控制器中的变量,然后使用该变量显示正确的奖励。像这样的:

 <div ng-controller="teamController">
   <div>
       <select ng-model="selectedTeamId">
         <option ng-repeat="t in teams" value="{{t.id}}">{{...}}</option>
       </select>
   </div>

  <div>
      // awards to go here
      {{awardInfo}}
  </div>
</div>

Javascript:

teamController.controller('teamListController', ['$scope', 'Team', 'Award',
    function($scope, Team, Award) {

        $scope.teams = Team.query();
        $scope.selectedTeamId = null;
        $scope.awardInfo = null;

        $scope.$watch('selectedTeamId', function(idValue) {
            if (idValue !== null) {
                $scope.awardInfo = Award.query({ teamId: idValue });
            }
        });
    }
]);

【讨论】:

    【解决方案2】:

    由于您需要在控制器之间共享选定的团队 ID,因此您必须使用某些东西来完成此操作。 Angular 对此有多种选择,但在这种情况下,我认为一个值就足够了。另外,我会将您的 select 切换为使用 ng-options 以使整个过程更容易。

    有很多方法可以实现这一点,但这里有一个示例可以帮助您入门。我伪造了一些数据,而且一切都只是使用了一个大的 angular.module() 链,你可能不应该在生产应用程序中这样做。

    我正在使用一个值在控制器之间共享团队 ID。值只不过是一个可以注入到任何 Angular 模块中的持久对象。在teamAwardsController 中,我正在关注SelectedTeam.id 属性的变化——当没有选择团队时,你必须处理,但这应该很容易。在teamListController 中,我将SelectedTeam 值分配给$scope 级别变量,以便可以直接在视图中读取和设置它。

    首先是JS:

    angular.module('app', [])
        .value('SelectedTeam', {
            id: -1
        })
        .service('FakeDataService', function() {
            this.GetTeams = function() {
                return [{
                    id: 1,
                    name: 'Portland Timbers',
                    weekNight: 'Monday',
                    year: '2016'
                }, {
                    id: 2,
                    name: 'Seattle Sounders',
                    weekNight: 'Tuesday',
                    year: '2016'
                }, {
                    id: 3,
                    name: 'LA Galaxy',
                    weekNight: 'Thursday',
                    year: '2016'
                }, {
                    id: 4,
                    name: 'San Jose Quakes',
                    weekNight: 'Wednesday',
                    year: '2016'
                }, ];
            };
        })
        .controller('teamListController', function($scope, FakeDataService, SelectedTeam) {
            $scope.selectedTeam = SelectedTeam;
            $scope.teams = FakeDataService.GetTeams();
        })
        .controller('teamAwardsController', function($scope, $log, SelectedTeam) {
            $scope.selectedTeam = SelectedTeam;
            $scope.$watch('selectedTeam.id', function() {
                $log.info('Team changed to ' + $scope.selectedTeam.id);
            });
        });
    

    现在是一些示例标记:

    <div ng-app='app'>
        <div ng-controller='teamListController'>
            <select ng-model='selectedTeam.id' ng-options='t.id as (t.year + " - " + t.name + " (" + t.weekNight + "s)") for t in teams'></select>
        </div>
        <div ng-controller='teamAwardsController'>
            Here is where would list the selected team's awards.
        </div>
    </div>
    

    【讨论】:

    • 好的。我知道了!您在这里得到的答案是我最初对如何获取数据的想法,但是您对我的 OP 的第一条评论确实是最有意义的,这就是 Mikes 解决方案的作用。我首先实现了这个解决方案,但由于两个控制器都有 selectedTeam 参数,我只需扩展包含控制器引用的 div 以包含奖项潜水,然后使用下面的 Mikes 解决方案。感谢大家的帮助!
    猜你喜欢
    • 2021-12-04
    • 1970-01-01
    • 2015-07-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-12-20
    • 1970-01-01
    相关资源
    最近更新 更多