RESTful的优点

 优点

1.通过url对资源定位,语义清晰;

2.通过HTTP谓词表示不同的操作,接口自描述;

3.可以对GET、PUT、DELETE请求重试(幂等的)

4.可以对GET请求做缓存;

5.通过HTTP状态码反映服务器端的处理结果,统一错误处理机制;

6.网关等可以分析请求处理结果。

请求重试-是幂等的,失败之后可以多次发起请求
做缓存-降低服务器的压力,响应速度更快
关键不同的状态码处理不同的请求返回
网关-可以检测发起的请求,若500太多的时候就会报错

Q点: 

有些浏览器与运营商会在你的响应报文里面加广告

示例restful使用

URL:适合定位,用于资源定位的

QuerySting:灵活,长度限制,通常为URL以外的数据

请求报文体:灵活,长度不限制,不支持GET与DELETE,供PUT、POST提供数据

/Student/火属性/Type/2/ON/6
/Student?Status=火属性&Type=2&ON=6

参考实施指南

1.对于保存、更新类的请求POST、PUT(幂等的)请求,把全部参数都放到请求报文体中;2.对于DELETE请求,要传递的参数就一个资源id,因此把参数放到QueryString中即可;

3.对于GET请求,一般参数的内容都不会太长,因此统一通过QueryString传递参数即可。对于极少数的参数内容超过URL限制的请求,由于GET、PUT请求都是幂等的,因此改查PUT请求把参数通过报文体传参。

 /User/5  PATCH //符合rustful风格,但具体使用那个看自己
{"email":"@ab.com","age":"5"}
/User  PATCH 
{"id":"5","email":"@ab.com","age":"5"}

/User/5 DELETE
/User?id=5 QueryString

如何返回错误码

 REST:通过HTTP状态码返回服务器端的处理结果

HTTP状态码不适合用于表示业务层面的错误码,它是一个用于表示技术层面的状态码。新增用户的操作中,如果服务器端要求JSON格式,客户端提交XML服务器返回400是没问题的。

但是如果用户名格式错误或者用户名重复,存在2xx与4xx。

 400 BadRequest

用户请求的数据格式有问题时:无论成功与失败都返回请求在返回的{"code":"201"}展示具体的错误原因。

400派观点:若前端都没做好校验就返回400,不能通过网关将请求发送到服务器。(google、微信支付)

1.网关等可以监控HTTP状态码,如果接口频繁出现4xx状态码,说明客户端代码不完善。

2.很多系统不同的状态码有不同的含义,如果失败的服务的返回值200违背设计的初衷。

3.有些网关会将返回304的请求重定向到登录页面,若直接返回200将无法跳转

 200派观点:网络的问题归网络、业务的问题归业务。(百度、微信小程序)

业务日志:返回200的看code的错误记录在此

技术日志:返回400、500记录在此

技术一个为业务服务

作者的个人观点

1.对于数据库服务器连接失败、请求报文格式、服务器端异常等业务错误,服务器端应返回4xx、5xx。

2.对于业务层面的错误,比如用户不存在,使用4xx等状态码返回。在报文中返回详细错误,{”code“:3,"message":"用户不存在"}。

3.不仅要返回400的HTTP状态码,不要忘了通过响应报文返回详细信息,指出问题出在哪里。

 实现建议

使用总结:

[Route("api/[controller]/[action]")]

User/DeleteUser(int id)

 

出现这个说明该接口不符合swagger的使用规则

接口中调用自定义的方法不能使用public定义只能使用private方法

了解:加上这段就可以使用public的方法了,一般不这么干了解

安照分层的原则, Controller层中一般是调用其他层定义的、所有上面的的代码只作了解。

ControllerBase与Controller

 Controller是继承自ControllerBase,在其基础上创建一些与视图有关的类以供使用MVC

也可以不继承任何类,可以方便后面做单元测试。 但不推荐,继承类的需要配置环境。

读取本地文件

[HttpGet]
public async Task<string> Add2()
{
    string s=await.ReadAllTextAsync("d:/log.log");
    return s.Substring(0,20);
}

Action方法的同步与异步

1.异步也可以同步

2.异步一般不需要async结尾

3.返回值为普通类型时,值默认序列号为JSON格式

4.IActionResult类型,不包含类型信息,因为swagger无法推断类型,推荐使用ActionResult<T>它支持类型转换。好处可以返回NotFind()

 总结:要么使用普通的数据类型要么使用ActionResult<T>

[HttpGet]
public string Add()
{
    return "yes";
}
//...
[HttpGet]
public ActionResult<IEnumerable<User>> GetUser()
{
    if(xxx)
{ 
   return NotFound()
}
return OK();
}

请求样式(更新)

//更新
[HttpPost("{id}")]
public async Task<ActionResult<IEnumerable<User>>> GetMag([fromRoute] int id, User m)
{
    //....
}

/updateuser/8
`/updateuser/${id}`
{
"name":"lyy",
"age":18
}

JSON报文体

1.webapi开发模式下、json格式的请求体是主流。

2.只要声明一个模型类和Json请求格式一致即可。

3.可以混用

4.一定要设置请求头中的Content-Type:application/json,而且数据必须是合法的json格式。

 util->index

// 引入axios
import axios from 'axios';
import {ElMessage} from "element-plus";

// 创建axios实例
const httpService = axios.create({
  // url前缀-'http:xxx.xxx'
  // baseURL: process.env.BASE_API, // 需自定义
  baseURL:'http://localhost:7137/',
  // 请求超时时间
  timeout: 3000 // 需自定义
});

//添加请求和响应拦截器
// 添加请求拦截器
httpService.interceptors.request.use(function (config) {
  // 在发送请求之前做些什么
  config.headers.token=window.sessionStorage.getItem('token');
  return config;
}, function (error) {
  // 对请求错误做些什么
  return Promise.reject(error);
});

// 添加响应拦截器
httpService.interceptors.response.use( response=> {
  // 对响应数据做点什么

      return response;
},
    function (error) {
  // 对响应错误做点什么
  return Promise.reject(error);
});

/*网络请求部分*/

/*
 *  get请求
 *  url:请求地址
 *  params:参数
 * */
export function get(url, params = {}) {
  return new Promise((resolve, reject) => {
    httpService({
      url: url,
      method: 'get',
      params: params
    }).then(response => {
      resolve(response);
    }).catch(error => {
      reject(error);
    });
  });
}

/*
 *  post请求
 *  url:请求地址
 *  params:参数
 * */
export function post(url, params = {}) {
  return new Promise((resolve, reject) => {
    httpService({
      url: url,
      method: 'post',
      data: params
    }).then(response => {
      console.log(response)
      resolve(response);
    }).catch(error => {
      console.log(error)
      reject(error);
    });
  });
}

/*
 *  文件上传
 *  url:请求地址
 *  params:参数
 * */
export function fileUpload(url, params = {}) {
  return new Promise((resolve, reject) => {
    httpService({
      url: url,
      method: 'post',
      data: params,
      headers: { 'Content-Type': 'multipart/form-data' }
    }).then(response => {
      resolve(response);
    }).catch(error => {
      reject(error);
    });
  });
}

export default {
  get,
  post,
  fileUpload
}

mvc的表单请求,需要请求头中获取数据

 

前后端分离开发

软件架构的一大主题就是分离,减少耦合

前后端分离技术为了利SEO,去启动”服务器渲染SSR“技术(前端知识)

 

示例

 //用户登录接口
 [HttpPost]
 public ActionResult<LoginResult> Login(LoginResult loginReq)
 {
     if (loginReq.UserName == 'admin' && loginReq.Pwd = "12345")
     {
         //数据库获取加载信息 var data=
         return new LoginResult(true, data);
     }
     else return new LoginResult(false, null);

 }

 record的作用?

登录示例

登录成功则返回当前服务器的进程信息

后端页面

//public record LoginRequest(string UserName, string Pwd);
//public record ProcessInfo(long Id,string UserName,long WorkSet);
//public record LoginResponse(bool Ok,string UserName,long WorkSet);

前端页面 

 

 

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值