使用AngularJS $location从URL中获取查询字符串的值

97
关于 $location.search文档中指出:

当没有参数调用时,返回当前URL的搜索部分(作为对象)。

在我的URL中,我的查询字符串有一个没有值的参数?test_user_bLzgB。此外,$location.search()返回一个对象。我该如何获得实际文本?


你得到了什么对象?你有一个 Plunkr 或 Fiddle 来演示你面临的问题吗?当你使用 $location.search() 时,你是正确的,但我想检查一下你调用它时得到的“对象”... - callmekatootie
我不知道这是什么对象。我尝试枚举属性,但似乎没有任何属性。 - Ian Warburton
不确定如何创建一个检查查询字符串的 fiddle。 - Ian Warburton
10个回答

155

我不确定自从被接受的答案被接受以来是否有更改,但是这是可能的。

$location.search()会返回一个键值对的对象,与查询字符串中的相同。没有值的关键字只存储为true。在本例中,该对象将如下所示:

{"test_user_bLzgB": true}

您可以直接使用$location.search().test_user_bLzgB访问此值。

示例(带有更长的查询字符串):http://fiddle.jshell.net/TheSharpieOne/yHv2p/4/show/?test_user_bLzgB&somethingElse&also&something=Somethingelse

注意:由于哈希(它将转到http://fiddle.jshell.net/#/url,这会创建一个新的fiddle),因此在不支持js历史记录的浏览器中(在IE <10中不起作用),此小提琴将无法正常工作。

编辑:
如@Naresh和@DavidTchepak在评论中指出的那样,$locationProvider也需要正确配置:https://code.angularjs.org/1.2.23/docs/guide/$location#-location-service-configuration


3
如Naresh所述,还需要正确配置$locationProvider:https://code.angularjs.org/1.2.23/docs/guide/$location#-location-service-configuration(这让我有些困惑。希望这个链接可以节省其他人的时间。) - David Tchepak
2
要配置位置提供者,您需要: window.app.config ['$locationProvider', ($locationProvider) -> $locationProvider.html5Mode true ] 您还需要在HTML文件中添加基本标记:<base href="/"> - Amin Ariana
感谢提供的灵感和有用的技巧,我想分享一下我的经验。我创建了一个名为userConfig的常量,并把所有东西都放在里面,某些设置可以通过查询字符串进行覆盖,以便用户更加灵活。我使用了这种方法,并将查询字符串放在全局控制器范围变量中,该变量位于HTML标记中,因此任何子控制器都可以获取参数,包括服务。由于userConfig也放在服务中,因此它们可以互相交互。 - 西門 正 Code Guy
我发现使用js函数更容易,$location.search()有太多的移动部件。有很多代码示例可以获取查询字符串参数。 - nuander
@TheSharpieOne 如果您有时间,能否看一下这个问题?http://stackoverflow.com/questions/43121888/where-to-capture-the-location-search-vars-in-the-run-statement-in-order-to-r - Leon Gaban

49
如果你只需要查看查询字符串的文本形式,可以使用:$window.location.search

11
这怎么不算是一个回答呢?也许有点简短,但它确实似乎回答了这个问题。 - Léo Lam
如果你查看时间戳,回答是在丹的评论之后2个小时进行编辑的。这并不是非常重要,但我发现令人震惊的是Leo的评论正在得到赞同,所以我想指出来。 - Bill Tarbell

41

$location.search() 返回一个对象,其中键为变量,值为其值。因此:如果您像这样编写查询字符串:

?user=test_user_bLzgB

你可以轻松地获取文本,方法如下:

$location.search().user
如果您不想使用键/值对的形式,例如?foo=bar,我建议使用哈希#test_user_bLzgB,并调用
$location.hash()

将返回'test_user_bLzgB',这是您希望检索的数据。

其他信息:

如果您使用查询字符串方法并且使用$location.search()返回空对象,则可能是因为Angular使用了hashbang策略而不是html5策略...为使其正常工作,请将此配置添加到您的模块中:

yourModule.config(['$locationProvider', function($locationProvider){
    $locationProvider.html5Mode(true);    
}]);

13

首先,使获取查询字符串的URL格式正确,使用#?q=string 对我有用

http://localhost/codeschool/index.php#?foo=abcd

将 $location 服务注入到控制器中

app.controller('MyController', [ '$location', function($location) { 

    var searchObject = $location.search();

    // $location.search(); reutrn object 
    // searchObject = { foo = 'abcd' };

    alert( searchObject.foo );

} ]);

因此输出应为abcd


10

您也可以使用这个

function getParameterByName(name) {
    name = name.replace(/[\[]/, "\\[").replace(/[\]]/, "\\]");
    var regex = new RegExp("[\\?&]" + name + "=([^&#]*)"),
        results = regex.exec(location.search);
    return results === null ? "" : decodeURIComponent(results[1].replace(/\+/g, " "));
}

var queryValue = getParameterByName('test_user_bLzgB');

3
你从别人的SOF答案中复制了那个函数...最好引用你的来源。 - arcseldon
是的,这就是我使用的,从 Stack Overflow 上某个地方得到的。 - nuander

10

如果你的$location.search()没有起作用,请确保你完成了以下步骤:

1)在应用程序模块配置中配置了html5Mode(true)

appModule.config(['$locationProvider', function($locationProvider) {
   $locationProvider.html5Mode(true);
}]);

2) 您的HTML中存在<base href="/">

<head>
  <base href="/">
  ...
</head>

参考文献:

  1. base href="/"
  2. html5Mode

"html5Mode(true)已在应用程序的模块配置中进行了配置" -- 解释 - 15ee8f99-57ff-4f92-890c-b56153
@EdPlunkett - 抱歉,我的意思是它是在Angular应用程序对象的config方法中配置的。例如,在这里: var appModule = angular.module('myAppModule', []); - Mahesh
谢谢,我对Angular还很陌生。 - 15ee8f99-57ff-4f92-890c-b56153
是的,这非常重要,我也曾面临同样的问题。 - Bahadir Tasdemir

7

Angular不支持这种类型的查询字符串。

URL的查询部分应该是一个以&分隔的键值对序列,因此可以完美地解释为对象。

没有任何API来管理不表示键值对集合的查询字符串。


0
在我的NodeJS示例中,我有一个URL“localhost:8080/Lists/list1.html?x1=y”,我想遍历并获取值。
为了使用$location.search()获取x1=y,我做了一些事情:
  1. 脚本源到angular-route.js
  2. 将“ngRoute”注入您的应用程序模块的依赖项中
  3. 配置您的locationProvider
  4. 添加$location的基本标记(如果不这样做,则搜索().x1将返回空或未定义。或者如果基本标记具有错误的信息,则您的浏览器将无法在.script src内找到您的文件,而您的.html需要。始终打开页面的视图源以测试您的文件位置!)
  5. 调用位置服务(search())
我的list1.js文件有:
    var app = angular.module('NGApp', ['ngRoute']);  //dependencies : ngRoute
    app.config(function ($locationProvider) { //config your locationProvider
         $locationProvider.html5Mode(true).hashPrefix('');
    });

    app.controller('NGCtrl', function ($scope, datasvc, $location) {// inject your location service
        //var val = window.location.href.toString().split('=')[1];
        var val = $location.search().x1;    alert(val);
        $scope.xout = function () {
           datasvc.out(val)
           .then(function (data) {
              $scope.x1 = val;
              $scope.allMyStuffs = data.all;
           });
        };
        $scope.xout();
    });

我的list1.html文件中有:

<head>
    <base href=".">
    </head>
<body ng-controller="NGCtrl">
<div>A<input ng-model="x1"/><br/><textarea ng-model="allMyStuffs"/></div>
<script src="../js/jquery-2.1.4.min.js"></script>
<script src="../js/jquery-ui.min.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.9/angular.min.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.9/angular-route.js"></script>
<script src="../js/bootstrap.min.js"></script>
<script src="../js/ui-bootstrap-tpls-0.14.3.min.js"></script>
<script src="list1.js"></script>
</body>

指南:https://code.angularjs.org/1.2.23/docs/guide/$location

0

我的解决方案更简单,创建一个工厂,并将其实现为一个变量。例如

angular.module('myApp', [])

// This a searchCustom factory. Copy the factory and implement in the controller
.factory("searchCustom", function($http,$log){    
    return {
        valuesParams : function(params){
            paramsResult = [];
            params = params.replace('(', '').replace(')','').split("&");
            
            for(x in params){
                paramsKeyTmp = params[x].split("=");
                
                // Si el parametro esta disponible anexamos al vector paramResult
                if (paramsKeyTmp[1] !== '' && paramsKeyTmp[1] !== ' ' && 
                    paramsKeyTmp[1] !== null){          
                    
                    paramsResult.push(params[x]);
                }
            }
            
            return paramsResult;
        }
    }
})

.controller("SearchController", function($scope, $http,$routeParams,$log,searchCustom){
    $ctrl = this;
    
    var valueParams = searchCustom.valuesParams($routeParams.value);
    valueParams = valueParams.join('&');

    $http({
        method : "GET",
        url: webservice+"q?"+valueParams
    }).then( function successCallback(response){
        data = response.data;
        $scope.cantEncontrados = data.length; 
        $scope.dataSearch = data;
        
    } , function errorCallback(response){
        console.log(response.statusText);
    })
      
})
<html>
<head>
</head>
<body ng-app="myApp">
<div ng-controller="SearchController">
<form action="#" >
                          
                            
                            <input ng-model="param1" 
                                   placeholder="param1" />
                            
                            <input  ng-model="param2" 
                                    placeholder="param2"/>
                        
<!-- Implement in the html code 
(param1={{param1}}&param2={{param2}}) -> this is a one variable, the factory searchCustom split and restructure in the array params
-->          
                        <a href="#seach/(param1={{param1}}&param2={{param2}})">
                            <buttom ng-click="searchData()" >Busqueda</buttom>
                        </a>
                    </form> 
</div>
</body>


0

非常晚的回答 :( 但对于需要的人来说,Angular js也可以使用 :) URLSearchParams 让我们看看如何使用这个新的API从位置获取值!

// 假设 "?post=1234&action=edit"

var urlParams = new URLSearchParams(window.location.search);
console.log(urlParams.has('post')); // true
console.log(urlParams.get('action')); // "edit"
console.log(urlParams.getAll('action')); // ["edit"]
console.log(urlParams.toString()); // "?post=1234&action=edit"
console.log(urlParams.append('active', '1')); // "?

post=1234&action=edit&active=1"

注意:IE不受支持

请使用此函数代替URLSearchParams

urlParam = function (name) {
    var results = new RegExp('[\?&]' + name + '=([^&#]*)')
                      .exec(window.location.search);

    return (results !== null) ? results[1] || 0 : false;
}

console.log(urlParam('action')); //edit

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接