66

テストサーバーにデプロイするまでは正常に機能していた次のコードがあります。

$scope.getUserList = function (userName) {
    $http({
        method: "get",
        url: "GetUserList",
        params: { userName: userName }
    }).
        success(function (data) {
            $scope.users = data;
        }).
        error(function () {
            alert("Error getting users.");

問題は、仮想ディレクトリに展開したことであり、以下の呼び出しはサーバー ルートから GetUserList をヒットしようとしています。これは理にかなっており、私はそれを修正する方法をいくつか知っています。

私が知りたいのは、Angular で移植可能で保守可能な方法でサービス URL を参照する正しい方法です。

4

9 に答える 9

105

head で HTML base タグを使用し、これに関連するすべてのパスをコーディングすることをお勧めします。たとえば、ASP.NET では、アプリケーションのベースへの参照を取得できます。これは、サイトのルート パスである場合とそうでない場合があるため、base タグを使用すると役立ちます。おまけ: 他のすべてのアセットでも機能します。

次のような基本パスを持つことができます。

<base href="/application_root/" />

...そして、「foo/bar.html」のようなリンクは、実際には /application_root/foo/bar.html になります。

私が好んで使用するもう 1 つの方法は、ヘッダーに名前付きリンクを配置することです。多くの場合、ある場所に API ルートがあり、別の場所にディレクティブ テンプレート ルートがあります。head に、次のようなタグを追加します。

<link id="linkApiRoot" href="/application_root/api/"/>
<link id="linkTemplateRoot" href="/application_root/Content/Templates/"/>

...そして、モジュールで $provide を使用してリンクの href を取得し、次のようにサービスとディレクティブに公開します。

angular.module("app.services", [])
    .config(["$provide", function ($provide) {
        $provide.value("apiRoot", $("#linkApiRoot").attr("href"));
    }]);

...そして、次のようにサービスに注入します。

angular.module("app.services").factory("myAdminSvc", ["apiRoot", function (apiRoot) {
    var apiAdminRoot = apiRoot + "admin/";
    ...

あくまで私の意見ですが。アプリケーションにとって最も複雑でないことを行います。

于 2013-06-09T19:39:20.360 に答える
13

<base>アプリケーションが別のオリジオンから動的にポップアップで作成されたため、タグを使用できませんでした。このスレッドのその他のオプションを検討して、basePath変数のようなものを使用し、すべての変数などで使用することを検討していまし$http, ng-src, templateUrl

しかし、それは少しオーバーヘッドがあり、xhr が作成される前にすべての URL を変更するインターセプターを構築しました

var app = angular.module("myApp", []);

app.config(["$httpProvider", function($httpProvider) {
    $httpProvider.interceptors.push('middleware');
}]);

app.factory('middleware', function() {
    return {
        request: function(config) {
            // need more controlling when there is more than 1 domain involved
            config.url = "//example.com/api/" + config.url
            return config;
        }
    };
});

app.controller("Ctrl", ["$http", function($http) {
    $http.get("books"); // actually requestUrl = http://example.com/api/books
}])

そしてhtmlも

<div ng-include src="'view'">
    <!-- actually src = http://example.com/api/view -->
</div>

<base>ただし、window.popup() を使用していない限り、代わりにタグを使用することをお勧めします。

于 2013-09-26T21:48:00.997 に答える
4

$location サービスを使用すると、パス、ハッシュ、サーバー アドレスが返されます。あなたの電話は、$location.path()+"/GetUserList"またはそれに似たものになります。

ここを参照してください: http://docs.angularjs.org/guide/dev_guide.services.$location

于 2013-06-09T16:24:55.797 に答える
2

受け入れられた答えは私を助けました。私はMVCアプリを提供するAngularを使用しています。Web API 呼び出しまたはテンプレートへのアクセスのために、角度コントローラー内で baseUrl を使用できるように、もう 1 つの手順を実行しました。

ng-init を使用して baseUrl を設定する (サーバー側で入力された値から)

<html ng-app="app" ng-controller="AppController">
<head>
    <base href="{{baseUrl}}" ng-init="baseUrl = '@Model.BaseUrl'" />
</head>

角度コントローラー

    $scope.manageCustomerGroups = function () {
        openDialog($scope.baseUrl + 'content/templates/customerGroups.html');
    }
于 2015-02-17T15:09:47.723 に答える
-1

ng-init 関数で、仮想ディレクトリ (Request.ApplicationPath に格納されている int ASP.NET) の値を含むパラメーターを渡します。

<div ng-controller="ControllerName" ng-init="init('@Request.ApplicationPath')">

angular コントローラー内で、この値をすべての http 呼び出しで URL のプレフィックスとして使用します。この関数を使用して、パスを結合できます

function combinePath(path1, path2) {
    if (path1 == null) {
        return path2;
    }
    var last = path1.slice(-1);
    var first = path2.charAt(0);

    if (last == '/' && first == '/') {
        path1 = path1.substring(0, path1.length - 1);
    }
    return path1 + path2;
}
于 2015-09-18T14:52:36.700 に答える