具有相同路径但不同参数的快速路由

bco*_*983 0 node.js express angularjs

我有两种方法:

  • validateRegistration(),它调用 app.get('/users/:email', todo)

  • login(),它调用 app.get('/users/:username', todo)

validateRegistration() 工作正常,但是当 login() 被调用时,它返回 null,但是如果我在 server.js 中注释掉 app.get('/users/:email', todo),login() 返回预期的响应. 似乎两者不能同时存在于 server.js

请参阅下面的相关代码

注册页面.html

<div class="container" ng-show="show">
		<form name="registerForm" novalidate>

			<h2>Registration</h2>
			<span>All fields required</span>
			<br>
			<br>
			<label>First Name</label>
			<br>
			<input class="form-control" type="text" ng-model="user.fName" name="fName" required placeholder="First Name">
			<div ng-messages="registerForm.fName.$error">
				<div class="errorMsg" ng-message="required">Required</div>
			</div>
			
			<br>
			<label>Last Name</label>
			<input class="form-control" type="text" ng-model="user.lName" name="lName" required placeholder="Last Name">
			<div ng-messages="registerForm.lName.$error">
				<div class="errorMsg" ng-message="required">Required</div>
			</div>

			<br>
			<label>Email</label>
			<input class="form-control" ng-model="user.email" ng-change="validateEmail(user.email)" type="email" name="emailAdd" required placeholder="Email">
			<span class="errorMsg">{{emailExistsMsg}}</span>

			<div ng-messages="registerForm.emailAdd.$error">
				<div class="errorMsg" ng-message="email">Invalid email address</div>
				<div class="errorMsg" ng-message="required">Required</div>
			</div>

			<br>
			<label>Username</label>
			<input class="form-control" ng-model="user.username" ng-change="validateUsername(user.username)" type="text" name="uName" required placeholder="Username">
			<span class="errorMsg">{{usernameExistsMsg}}</span>
			<div ng-messages="registerForm.uName.$error">
				<div class="errorMsg" ng-message="required">Required</div>
			</div>

			<br>
			<label>Password</label>
			<input class="form-control" ng-minlength="6" type="password" ng-model="user.password" name="password" required placeholder="Password">
			<div ng-messages="registerForm.password.$error">
				<div class="errorMsg" ng-message="minlength">Password should be 6 character minimum</div>
				<div class="errorMsg" ng-message="required">Required</div>
			</div>

			<br>
			<button class="btn btn-info" ng-click="addUser(user)" ng-disabled="registerForm.$invalid">Register</button>
			<br>
			<br>
			<a href="#/signIn">Already registered?......<strong>Log In</strong></a>
	</form>
</div>
Run Code Online (Sandbox Code Playgroud)

注册控制器.js

myApp.controller('RegisterController', ['$scope', '$http', '$location', function($scope, $http, $location) {
	console.log("Register controller");

	$scope.addUser = function(user) {
		console.log("Add user called");
		$http.post('/users', {fname: user.fName, lname: user.lName, email: user.email, username: user.username, password: user.password}).success(function(response) {
			console.log("Add user response username: " + response.username);
		});

		this.validateRegistration(user.email);
	};

	$scope.validateEmail = function(email) {
		console.log("Validate email called");
		$http.get('/users/' + email).success(function(response) {
			if(response != null) {
				$scope.emailExistsMsg = response.email + " already exists";
			} else {
				$scope.emailExistsMsg = "";
			}
		});
	};

	$scope.validateRegistration = function(email) {
		$http.get('/users/' + email).success(function(response) {
			if(response != null) {
				console.log("Registration successful");
				$scope.registrationMsg = "Congratulations " + email + ". Registration successful";
				console.log($scope.registrationMsg);
				$location.path("/registrationStatus");

			} else {
				console.log("Registration not successful: " + response);
				$scope.registrationMsg = "Error with registration. Please try again or contact administrator.";
				console.log($scope.registrationMsg);
				$location.path("/registrationStatus");
			}
		});
	};
}]);
Run Code Online (Sandbox Code Playgroud)

登录页面.html

<div class="container" ng-show="show">

	<br>
	<form name="signInForm" novalidate>
		<h2>Sign In</h2>
		<br>
		<label>Username</label>
		<input class="form-control" ng-model="user.username" type="text" name="username" required placeholder="Username">
		<br>
		<label>Password</label>
		<input class="form-control" ng-model="user.password" type="password" name="password" required placeholder="Password">
		<br>
		<button class="btn btn-info" ng-click="logIn(user.username, user.password)" ng-disabled="signInForm.$invalid">Sign In</button>
		<br>
		<br>
		<a href="#/register">Not registered?......<strong>Register</strong></a>
	</form>

</div>
Run Code Online (Sandbox Code Playgroud)

登录控制器.js

myApp.controller('SignInController', ['$scope', '$http', '$location', function($scope, $http, $location) {
	console.log("Sign in controller");

	$scope.logIn = function(username, password) {
		console.log("Sign in called");

		$http.get('/users/' + username).success(function(response) {
			if(response != null) {
				if(username == response.username && password == response.password) {
					console.log("Successful log in");
					this.isDisabled = false;
					$location.path("/playSet");
				}
			} else {
				console.log("User not found: " + response);
			}
		});
	};
}]);
Run Code Online (Sandbox Code Playgroud)

服务器.js

var express = require('express');
var app = express();
var mongojs = require('mongojs');
var db = mongojs('tracks', ['tracks']);
var db1 = mongojs('setlist', ['setlist']);
var db2 = mongojs('users', ['users']);
var bodyParser = require('body-parser');

app.use(express.static(__dirname = '\public'));
app.use(bodyParser.json());

app.get('/users/:email', function(req, res) {
	var email = req.params.email;
	console.log("Existing email validation: " + email);
	db2.users.findOne({email: email}, function(err, doc) {
		res.json(doc);
	});
});

app.get('/users/:username', function(req, res) {
	var username = req.params.username;
	console.log("User: " + username);
	db2.users.findOne({username: username}, function(err, doc) {
		res.json(doc);
	});
});

app.listen(3000);
console.log("Server running on port 3000");
Run Code Online (Sandbox Code Playgroud)

jfr*_*d00 9

你不能有两条独立的路线:

app.get('/users/:email', ...);
app.get('/users/:username', ...);
Run Code Online (Sandbox Code Playgroud)

因为第二个永远不会被击中,因为第一个匹配相同的东西。您有以下选择:

  1. 更改一个路径,使其与另一个路径不同。
  2. 将它们组合成一个路由处理程序,并设计如何根据其他条件(查询参数、cookie、会话状态等)判断您要执行的逻辑片段。
  3. 使用更复杂的路由定义(可能包括正则表达式),以便每个路由定义您实际上都能分辨出两条路由之间的区别。

如果(我只是从你的上下文中猜测),你试图支持两种不同的用户识别方式(一种是用户名,另一种是电子邮件地址),那么我建议你将它们结合起来进入一个路由处理程序,然后只检查该:username值以查看它是用户名还是电子邮件地址,并在您的路由中进行相应操作。如果@用户名中不允许使用该符号,但电子邮件地址中需要该符号,则此方法可行。然后,您可以检查是否req.params.username包含@符号,如果包含,则分支到电子邮件地址逻辑。

// single route handler to handle either a username or email lookup
app.get('/users/:username', function(req, res) {
    var username = req.params.username;
    if (username.indexOf("@") !== -1) {
        console.log("Existing email validation: " + username);
        db2.users.findOne({email: username}, function(err, doc) {
            res.json(doc);
        });
    } else {
        console.log("User: " + username);
        db2.users.findOne({username: username}, function(err, doc) {
            res.json(doc);
        });
    }
});
Run Code Online (Sandbox Code Playgroud)

或者,也许更干一点:

// single route handler to handle either a username or email lookup
app.get('/users/:username', function(req, res) {
    // lookup either email address or username
    let name = req.params.username;
    let lookupObj = name.indexOf("@") !== -1 ? {email: name} : {username: name};
    db2.users.findOne(lookupObj, function(err, doc) {
        res.json(doc);
    });
});
Run Code Online (Sandbox Code Playgroud)

或者,您可以使用独特的路径将路线分开:

app.get('/users/email/:email', ...);
app.get('/users/userID/:username', ...);
Run Code Online (Sandbox Code Playgroud)