javascript - 发出请求后获得了错误的 request.body(值和名称放错了位置)
问题描述
几个月以来,我一直是编码初学者,但遇到了一个我无法解决的问题:
在我的角度应用程序中,我正在发出一个帖子请求(followUser):
import { Injectable } from '@angular/core';
import {HttpClient} from '@angular/common/http'
import {Observable} from 'rxjs';
@Injectable({
providedIn: 'root'
})
export class UsersService {
constructor(private http : HttpClient) { }
getAllUsers() : Observable<any> {
return this.http.get('http://localhost:8080/chatApp/users')
}
followUser(userFollowed) : Observable<any> {
console.log(userFollowed);
return this.http.post('http://localhost:8080/chatApp/follow-user', {
userFollowed
});
}
}
userFollowed 是一个包含 ID 的对象(console.log 返回 5da24df09a3e662fd437d21b)
然而,当我在我的节点后端收到这个对象时,我只是 console.log 像这样:
followUser (req,res) {
console.log(req.body);}
我从控制台获得这个:
{ '{"userFollowed":"5da24df09a3e662fd437d21b"}': '' }
同样如您所见,这是一团糟,我不知道如何解决(我无法访问我的 userFollowed 值)
编辑:关注的用户是一个简单的对象,正如我在前面的 console.log(request.body) 中的评论部分所说,我获得了我期望的值:
{userFollowed:"5da24df09a3e662fd437d21b"}
当我在我的后端得到它并且我 console.log(request.body) 我得到{ '{"userFollowed":"5da24df09a3e662fd437d21b"}': '' }
编辑 2:我将涉及 userFollowed 的整个代码放在下面:
<div class = "container" style = "margin-top : 30px">
<div class = "row">
<div class = "col s12 m4 13">
</div>
<div class = "col s12 m8 19">
<div class = "rox">
<div class = "col s 12 m6 14 cardDiv" *ngFor = "let user of users">
<div class = "card">
<a>
<div class = "card-image imgDiv">
<img class = "imgCircle responsive-img" src = "http://placehold.it/100x100">
</div>
</a>
<div class = "card-action">
<h3 class = "card-title">
{{user.username}}
ici sont les username normalement :/
</h3>
<p>country</p>
<button class = "btn" (click)= "followUser(user)">follow</button>
<!--" need to add this instead of /chat solo-->
<a class = "secondary-content" [routerLink] = "['/chat', user.username]">
<i clas = "material-icons">chat</i>
</a>
</div>
</div>
</div>
</div>
</div>
</div>
以及与之链接的 TS 文件:
import { Component, OnInit } from '@angular/core';
import {UsersService} from './../../services/users.service';
import _ from 'lodash';
import {AuthenticationService } from '../../services/authentication.service';
@Component({
selector: 'app-people',
templateUrl: './people.component.html',
styleUrls: ['./people.component.scss'],
})
export class PeopleComponent implements OnInit {
users = [];
loggedInUser : any;
constructor( private usersService : UsersService, private authService : AuthenticationService) { }
ngOnInit() {
this.loggedInUser = this.authService.userData;
this.getUsers();
}
getUsers () {
this.usersService.getAllUsers().subscribe (data =>{
_.remove(data.result, {username : this.loggedInUser.username});
this.users=data.result;
console.log(this.users);
});
}
followUser(user) {
console.log(user._id);
this.usersService.followUser(user._id).subscribe(data=> {
console.log(data);
})
}
}
编辑 3:我的节点如下所示:
const express = require('express');
const bodyParser = require('body-parser');
const logger = require('morgan');
const methodOverride = require('method-override')
const cors = require('cors');
const mysql = require('mysql');
// Token handling :
const jwt = require('jsonwebtoken');
const config = require('./config/config');
//disk storage :
const multer = require('multer');
// password hashing :
const bcrypt = require('bcrypt');
const saltRounds = 10;
const dateTime = require ('date-time');
const nodemailer = require('nodemailer');
// ---------------------------------------
const connection = mysql.createConnection({ // a placer dans une variable environnementale
});
var app = express();
app.use(logger('dev'));
app.use(bodyParser.json());
app.use(methodOverride());
app.use(cors());
app.use(bodyParser.urlencoded({ extended: true }));
// TUTO PATRICK MONGODB
const mongoose = require('mongoose');
const dbConfig = require ('./config/secret');
const message = require ('./routes/messageRoutes');
const auth = require ('./routes/authRoutes');
const users = require('./routes/userRoutes');
const friends = require ('./routes/friendsRoutes');
mongoose.Promise = global.Promise;
mongoose.connect(
dbConfig.url,
{ useNewUrlParser : true}
);
app.use ('/chatApp', auth);
app.use('/chatApp', message );
app.use('/chatApp', users);
app.use('/chatApp', friends);
app.use(express.json());
然后路线:
const express = require('express');
const router = express.Router();
const friendCtrl = require('../controllers/friends.js');
const authHelper = require("../helpers/authHelper");
router.post('/follow-user', authHelper.ProtectedRoutes, friendCtrl.followUser);
module.exports = router;
然后执行的代码
var User = require('../Models/userModels');
module.exports = {
followUser (req,res) {
console.log(req.body);};
解决方案
因此,感谢那些试图提供帮助的人,发生的事情是我的 HTTP 拦截器设置了两次标头(application/json 和 application/x-www-form-urlencoded),导致 bodyparserJson 和 bodyparserUrlencoded 都解析我的请求,这确实导致了奇怪的结果。错误的代码拦截器:
import {
HttpRequest,
HttpHandler,
HttpEvent,
HttpInterceptor,
HttpResponse,
HttpErrorResponse
} from '@angular/common/http';
import { Observable, throwError, from } from 'rxjs';
import { ToastController } from '@ionic/angular';
import {Storage} from '@ionic/storage';
import { switchMap } from 'rxjs/operators';
import {AuthenticationService} from './../services/authentication.service';
@Injectable({
providedIn: 'root'
})
export class TokenInterceptorService implements HttpInterceptor {
constructor(public toastController: ToastController, private storage : Storage) {}
intercept(request: HttpRequest<any>, next: HttpHandler) : Observable<HttpEvent<any>>{
const TOKEN_KEY ='ACCES_TOKEN';
console.log("requete avant",request.body);
return from(this.storage.get(TOKEN_KEY))
.pipe(
switchMap(token => {
if (token){
console.log("InterceptedHTTPRequest")
const headers = request.headers
.set('x-access-token', token)
.append('Content-Type', 'application/x-www-form-urlencoded'); // application/json instead of application/x-www..., had to use the 2nd one because of CORS blocked in chrome
const requestClone = request.clone({
headers
});
console.log("request interceptée et clonée");
console.log("request apres",requestClone.body);
return next.handle(requestClone);
}
else {
return next.handle(request);
}
}),
);
}
}
更正的拦截器:
import {
HttpRequest,
HttpHandler,
HttpEvent,
HttpInterceptor,
HttpResponse,
HttpErrorResponse
} from '@angular/common/http';
import { Observable, throwError, from } from 'rxjs';
import { ToastController } from '@ionic/angular';
import {Storage} from '@ionic/storage';
import { switchMap } from 'rxjs/operators';
import {AuthenticationService} from './../services/authentication.service';
@Injectable({
providedIn: 'root'
})
export class TokenInterceptorService implements HttpInterceptor {
constructor(public toastController: ToastController, private storage : Storage) {}
intercept(request: HttpRequest<any>, next: HttpHandler) : Observable<HttpEvent<any>>{
const TOKEN_KEY ='ACCES_TOKEN';
console.log("requete avant",request.body);
return from(this.storage.get(TOKEN_KEY))
.pipe(
switchMap(token => {
if (token){
console.log("InterceptedHTTPRequest")
const headers = request.headers
.append('x-access-token', token)
const requestClone = request.clone({
headers
});
console.log("request interceptée et clonée");
console.log("request apres",requestClone.body);
return next.handle(requestClone);
}
else {
return next.handle(request);
}
}),
);
}
}
推荐阅读
- python - Pandas 在数据的第 7 行之后混淆了日月 - 如何修复?
- r - R: 排名与 ties.method = 平均不显示小数排名
- c# - 动态返回类型 ActionResult 的正确语法
由显式 ActionResult 使用 和别的 - python - 为什么我在命令提示符中找不到 PIP?
- java - 模式匹配删除 wiki 标记标签
- python - 具有数据框条件的列表理解;ValueError:项目长度错误
- docusignapi - DocuSign:DocuSign REST API 服务的 IP 地址
- python - Python:在 Mac 上安装 wx 失败
- java - 如何使用 RabbitMQ 和 Spring Boot 将批量电子邮件发送到电子邮件地址列表?
- javascript - Dash:实现跟踪高亮回调