一区二区三区在线-一区二区三区亚洲视频-一区二区三区亚洲-一区二区三区午夜-一区二区三区四区在线视频-一区二区三区四区在线免费观看

服務器之家:專注于服務器技術及軟件下載分享
分類導航

PHP教程|ASP.NET教程|Java教程|ASP教程|編程技術|正則表達式|C/C++|IOS|C#|Swift|Android|VB|R語言|JavaScript|易語言|vb.net|

服務器之家 - 編程語言 - Java教程 - SpringBoot中的內容協商器圖解

SpringBoot中的內容協商器圖解

2021-02-23 11:11波波維奇 Java教程

本文通過圖文解說加代碼的形式給大家介紹了SpringBoot中的內容協商器知識,需要的朋友參考下吧

背景

使用了restful的小伙伴對于導出這些需求本能就是拒絕的~破壞了restful的url的一致性【嚴格矯正 不是http json就是restful 很多小伙伴都會吧暴露出一個json就直接稱為restful 】

正如上文的代碼生成器 我們會批量生成一堆代碼 其中絕大部分都是restcontroller

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
public abstract class abstractrestcontroller<v extends vo, s extends so, pk extends serializable> {
  protected class<v> voclazz;
  @autowired
  private service<v, s, pk> service;
  public abstractrestcontroller() {
    typetoken<v> votype = new typetoken<v>(getclass()) {
    };
    voclazz = (class<v>) votype.getrawtype();
  }
  @postmapping()
  @apioperation(value = "新建實體", notes = "")
  public result add(@requestbody v vo) {
    service.saveselective(vo);
    return resultgenerator.gensuccessresult();
  }
  @deletemapping("/{id}")
  @apioperation(value = "刪除實體", notes = "")
  public result delete(@pathvariable pk id) {
    service.deletebyid(id);
    return resultgenerator.gensuccessresult();
  }
  @putmapping
  @apioperation(value = "更新實體", notes = "")
  public result update(@requestbody v vo) {
    service.updatebyprimarykeyselective(vo);
    return resultgenerator.gensuccessresult();
  }
  @getmapping
  @apioperation(value = "獲取實體列表", notes = "")
  public result list(s so) {
    pagehelper.startpage(so.getcurrentpage(), so.getpagesize());
    list<v> list = service.findall();
    pageinfo pageinfo = new pageinfo(list);
    excelexportparam();
    return resultgenerator.gensuccessresult(pageinfo);
  }
  protected void excelexportparam() {
    exportparams ep = new exportparams(null, "數據");
    excelexportparam<v> param = new excelexportparam<>();
    param.setclazz(voclazz);
    param.setexcelexport(excelexport.normalexcel);
    param.setexportparams(ep);
    param.setfilename("文件.xls");
    f6static.setexcelexportparam(param);
  }
  @getmapping("/{id}")
  @apioperation(value = "獲取單個實體", notes = "")
  public result detail(@pathvariable pk id) {
    v vo = service.findbyid(id);
    return resultgenerator.gensuccessresult(vo);
  }
  @deletemapping("/batch")
  @apioperation(value = "批量刪除實體", notes = "")
  public result batchdelete(@requestparam string ids) {
    service.deletebyids(ids);
    return resultgenerator.gensuccessresult();
  }
  @getmapping("/batch")
  @apioperation(value = "批量獲取實體", notes = "")
  public result batchdetail(@requestparam string ids) {
    list<v> vos = service.findbyids(ids);
    return resultgenerator.gensuccessresult(vos);
  }
  @postmapping("/batch")
  @apioperation(value = "批量新建實體", notes = "")
  public result add(@requestbody list<v> vos) {
    service.save(vos);
    return resultgenerator.gensuccessresult();
  }
  @getmapping("/count")
  @apioperation(value = "獲取實體數目", notes = "")
  public result count(@requestbody v v) {
    int count = service.selectcount(v);
    return resultgenerator.gensuccessresult(count);
  }

那么導出如何做呢?【其實可以理解成導出就是數據的展示 不過此時結果不是json而已】

拋出一個問題那么登錄登出呢?傳統的方案都是login logout 那么換成restful資源的思路是啥呢?

提示: 登錄就是session的新建 登出就是session的刪除

實現

基于上述思路 我們自然就想到了那么我們只需要對同一個url返回多種結果不就ok了?【pdf一個版本 json一個版本 xml一個版本 xls一個版本】

bingo!這個是內容協商器的由來

內容協商器并不是spring創造出來的 事實上這個從http頭里面也能看出

SpringBoot中的內容協商器圖解

1.比如給英語客戶返回英語頁面 過于客戶返回漢語頁面

http 協議中定義了質量值(簡稱 q 值),允許客戶端為每種偏好類別列出多種選項,并為每種偏好選項關聯一個優先次序。

?
1
accept-language: en;q=0.5, fr;q=0.0, nl;q=1.0, tr;q=0.0

其中 q 值的范圍從 0.0 ~ 1.0(0.0 是優先級最低的,而 1.0 是優先級最高的)。

注意,偏好的排列順序并不重要,只有與偏好相關的 q 值才是重要的

2.那么還有其他的一些參數 比如 accept-header

通常是先內容協商器有如下幾種方案

1.使用accept header:

這一種為教科書中通常描述的一種,理想中這種方式也是最好的,但如果你的資源要給用戶直接通過瀏覽器訪問(即html展現),那么由于瀏覽器的差異,發送上來的accept header頭將是不一樣的. 將導致服務器不知要返回什么格式的數據給你. 下面是瀏覽器的accept header   

?
1
2
3
4
5
6
chrome:
   accept:application/xml,application/xhtml+xml,textml;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5    
   firefox:
   accept:text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8     
   ie8:
   accept:image/gif, image/jpeg, image/pjpeg, image/pjpeg, application/x-shockwave-flash, application/x-silverlight, application/x-ms-application, application/x-ms-xbap, application/vnd.ms-xpsdocument, application/xaml+xml, */*

2.使用擴展名

喪失了同一url多種展現的方式,但現在這種在實際環境中是使用最多的.因為更加符合程序員的審美觀.

比如/user.json /user.xls /user.xml

使用參數 現在很多open api是使用這種方式,比如淘寶

但是對于不同瀏覽器可能accept-header并不是特別統一 因此許多實現選擇了2 3兩種方案

我們在spring中采用上述兩種方案

首先配置內容協商器

代碼

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
@bean
  public viewresolver contentnegotiatingviewresolver(
      contentnegotiationmanager manager) {
    // define the view resolvers
    viewresolver beannameviewresolver = new beannameviewresolver();
    list<viewresolver> resolvers = lists.newarraylist(beannameviewresolver);
    contentnegotiatingviewresolver resolver = new contentnegotiatingviewresolver();
    resolver.setviewresolvers(resolvers);
    resolver.setcontentnegotiationmanager(manager);
    return resolver;
  }
  @override
  public void configurecontentnegotiation(contentnegotiationconfigurer configurer) {
    configurer.favorpathextension(true)
        .usejaf(false)
        .favorparameter(true)
        .parametername("format")
        .ignoreacceptheader(true)
        .defaultcontenttype(mediatype.application_json)
        .mediatype("json", mediatype.application_json)
        .mediatype("xls", excel_media_type);
  }

創建對應的轉換器

?
1
2
3
4
private httpmessageconverter<object> createexcelhttpmessageconverter() {
  excelhttpmessageconverter excelhttpmessageconverter = new excelhttpmessageconverter();
  return excelhttpmessageconverter;
}

直接使用easy-poi導出數據

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
/*
 * copyright (c) 2017. lorem ipsum dolor sit amet, consectetur adipiscing elit.
 * morbi non lorem porttitor neque feugiat blandit. ut vitae ipsum eget quam lacinia accumsan.
 * etiam sed turpis ac ipsum condimentum fringilla. maecenas magna.
 * proin dapibus sapien vel ante. aliquam erat volutpat. pellentesque sagittis ligula eget metus.
 * vestibulum commodo. ut rhoncus gravida arcu.
 */
package com.f6car.base.web.converter;
import cn.afterturn.easypoi.excel.excelexportutil;
import com.f6car.base.common.result;
import com.f6car.base.core.excelexport;
import com.f6car.base.core.excelexportparam;
import com.github.pagehelper.pageinfo;
import com.google.common.collect.lists;
import org.apache.poi.ss.usermodel.workbook;
import org.springframework.http.httpheaders;
import org.springframework.http.httpinputmessage;
import org.springframework.http.httpoutputmessage;
import org.springframework.http.mediatype;
import org.springframework.http.converter.abstracthttpmessageconverter;
import org.springframework.http.converter.generichttpmessageconverter;
import org.springframework.http.converter.httpmessagenotreadableexception;
import org.springframework.http.converter.httpmessagenotwritableexception;
import java.io.ioexception;
import java.lang.reflect.type;
import java.net.urlencoder;
import java.util.collection;
import java.util.collections;
import java.util.map;
import static com.f6car.base.core.f6static.getexcelexportparam;
/**
 * @author qixiaobo
 */
public class excelhttpmessageconverter extends abstracthttpmessageconverter<object>
    implements generichttpmessageconverter<object> {
  public static final mediatype excel_media_type = new mediatype("application", "vnd.ms-excel");
  public excelhttpmessageconverter() {
    super(excel_media_type);
  }
  @override
  protected boolean supports(class<?> clazz) {
    return false;
  }
  @override
  protected object readinternal(class<?> clazz, httpinputmessage inputmessage) throws ioexception, httpmessagenotreadableexception {
    return null;
  }
  @override
  protected void writeinternal(object o, httpoutputmessage outputmessage) throws ioexception, httpmessagenotwritableexception {
    httpheaders headers = outputmessage.getheaders();
    collection data = getactualdata((result) o);
    excelexportparam excelexportparam = getexcelexportparam();
    workbook workbook;
    switch (excelexportparam.getexcelexport()) {
      case normalexcel:
        workbook = excelexportutil.exportexcel(
            excelexportparam.getexportparams(),
            (class<?>) excelexportparam.getclazz(),
            (collection<?>) data);
        break;
      case mapexcel:
        workbook = excelexportutil.exportexcel(
            excelexportparam.getexportparams(),
            excelexportparam.getexcelexportentities(),
            (collection<? extends map<?, ?>>) data);
        break;
      case bigexcel:
      case mapexcelgraph:
      case pdftemplate:
      case templateexcel:
      case templateword:
      default:
        throw new runtimeexception();
    }
    if (workbook != null) {
      if (excelexportparam.getfilename() != null) {
        string codedfilename = urlencoder.encode(excelexportparam.getfilename(), "utf8");
        headers.setcontentdispositionformdata("attachment", codedfilename);
      }
      workbook.write(outputmessage.getbody());
    }
  }
  private collection getactualdata(result r) {
    if (r != null && r.getdata() != null) {
      object data = r.getdata();
      if (data instanceof pageinfo) {
        return ((pageinfo) data).getlist();
      } else if (!(data instanceof collection)) {
        data = lists.newarraylist(data);
      } else {
        return (collection) data;
      }
    }
    return collections.emptylist();
  }
  @override
  public boolean canread(type type, class<?> contextclass, mediatype mediatype) {
    //不支持excel
    return false;
  }
  @override
  public object read(type type, class<?> contextclass, httpinputmessage inputmessage) throws ioexception, httpmessagenotreadableexception {
    return null;
  }
  @override
  public boolean canwrite(type type, class<?> clazz, mediatype mediatype) {
    return super.canwrite(mediatype) && clazz == result.class && support();
  }
  private boolean support() {
    excelexportparam param = getexcelexportparam();
    if (param == null || param.getexcelexport() == null || param.getexportparams() == null) {
      return false;
    }
    if (param.getexcelexport() == excelexport.normalexcel) {
      return true;
    } else {
      logger.warn(param.getexcelexport() + " not supprot now!");
      return false;
    }
  }
  @override
  public void write(object o, type type, mediatype contenttype, httpoutputmessage outputmessage) throws ioexception, httpmessagenotwritableexception {
    super.write(o, contenttype, outputmessage);
  }
}

暫時只是針對導出 因此在使用的時候如下

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
@getmapping
 @apioperation(value = "獲取實體列表", notes = "")
 public result list(s so) {
   pagehelper.startpage(so.getcurrentpage(), so.getpagesize());
   list<v> list = service.findall();
   pageinfo pageinfo = new pageinfo(list);
   excelexportparam();
   return resultgenerator.gensuccessresult(pageinfo);
 }
 protected void excelexportparam() {
   exportparams ep = new exportparams(null, "數據");
   excelexportparam<v> param = new excelexportparam<>();
   param.setclazz(voclazz);
   param.setexcelexport(excelexport.normalexcel);
   param.setexportparams(ep);
   param.setfilename("文件.xls");
   f6static.setexcelexportparam(param);
 }

當我們訪問時如下

 

SpringBoot中的內容協商器圖解

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
{
 "code": 200,
 "data": {
 "endrow": 10,
 "firstpage": 1,
 "hasnextpage": true,
 "haspreviouspage": false,
 "isfirstpage": true,
 "islastpage": false,
 "lastpage": 8,
 "list": [
 {
 "cellphone": "13857445502",
 "idemployee": 24201883434352650,
 "idownorg": 23993199378825296,
 "idrole": 88,
 "idwxbstation": "332",
 "idwxbuser": "207",
 "isadmin": 1,
 "isdel": 0,
 "isguideopen": 0,
 "limitmac": 0,
 "openid": "",
 "password": "96e79218965eb72c92a549dd5a330112",
 "pkid": 23993199378825296,
 "username": "lingweiqiche"
 },
 {
 "cellphone": "",
 "idemployee": 0,
 "idownorg": 9999,
 "idrole": 4,
 "idwxbstation": "",
 "idwxbuser": "",
 "isadmin": 0,
 "isdel": 0,
 "isguideopen": 0,
 "limitmac": 0,
 "openid": "",
 "password": "96e79218965eb72c92a549dd5a330112",
 "pkid": 24201883434356532,
 "username": "007"
 },
 {
 "cellphone": "15715139000",
 "idemployee": 24351585207523460,
 "idownorg": 24201883434357600,
 "idrole": 89,
 "idwxbstation": "540",
 "idwxbuser": "298",
 "isadmin": 1,
 "isdel": 0,
 "isguideopen": 0,
 "limitmac": 0,
 "openid": "",
 "password": "96e79218965eb72c92a549dd5a330112",
 "pkid": 24201883434357600,
 "username": "15715139000"
 },
 {
 "cellphone": "",
 "idemployee": 0,
 "idownorg": 24201883434357600,
 "idrole": 216,
 "idwxbstation": "",
 "idwxbuser": "",
 "isadmin": 0,
 "isdel": 0,
 "isguideopen": 0,
 "limitmac": 0,
 "openid": "",
 "password": "96e79218965eb72c92a549dd5a330112",
 "pkid": 24201883434357920,
 "username": "sunlingli"
 },
 {
 "cellphone": "",
 "idemployee": 24351585207425676,
 "idownorg": 24201883434359384,
 "idrole": 90,
 "idwxbstation": "348",
 "idwxbuser": "227",
 "isadmin": 1,
 "isdel": 0,
 "isguideopen": 0,
 "limitmac": 0,
 "openid": "opzuds_v13we500kxymj6xg_gfee",
 "password": "96e79218965eb72c92a549dd5a330112",
 "pkid": 24201883434359388,
 "username": "15952920979"
 },
 {
 "cellphone": "",
 "idemployee": 0,
 "idownorg": 24201883434359790,
 "idrole": 91,
 "idwxbstation": "315",
 "idwxbuser": "175",
 "isadmin": 1,
 "isdel": 0,
 "isguideopen": 0,
 "limitmac": 0,
 "openid": "",
 "password": "96e79218965eb72c92a549dd5a330112",
 "pkid": 24201883434359790,
 "username": "13809056211"
 },
 {
 "cellphone": "18903885585",
 "idemployee": 24201883434366164,
 "idownorg": 24201883434359890,
 "idrole": 92,
 "idwxbstation": "317",
 "idwxbuser": "178",
 "isadmin": 1,
 "isdel": 0,
 "isguideopen": 0,
 "limitmac": 0,
 "openid": "",
 "password": "96e79218965eb72c92a549dd5a330112",
 "pkid": 24201883434359892,
 "username": "18903885585"
 },
 {
 "cellphone": "",
 "idemployee": 24351585207425668,
 "idownorg": 24201883434359924,
 "idrole": 93,
 "idwxbstation": "318",
 "idwxbuser": "179",
 "isadmin": 1,
 "isdel": 0,
 "isguideopen": 0,
 "limitmac": 0,
 "openid": "",
 "password": "96e79218965eb72c92a549dd5a330112",
 "pkid": 24201883434359930,
 "username": "13372299595"
 },
 {
 "cellphone": "",
 "idemployee": 0,
 "idownorg": 24201883434360052,
 "idrole": 94,
 "idwxbstation": "321",
 "idwxbuser": "188",
 "isadmin": 1,
 "isdel": 0,
 "isguideopen": 0,
 "limitmac": 0,
 "openid": "",
 "password": "96e79218965eb72c92a549dd5a330112",
 "pkid": 24201883434360052,
 "username": "15221250005"
 },
 {
 "cellphone": "",
 "idemployee": 0,
 "idownorg": 24201883434360070,
 "idrole": 95,
 "idwxbstation": "325",
 "idwxbuser": "198",
 "isadmin": 1,
 "isdel": 0,
 "isguideopen": 0,
 "limitmac": 0,
 "openid": "",
 "password": "96e79218965eb72c92a549dd5a330112",
 "pkid": 24201883434360070,
 "username": "13837251167"
 }
 ],
 "navigatefirstpage": 1,
 "navigatelastpage": 8,
 "navigatepages": 8,
 "navigatepagenums": [
 1,
 2,
 3,
 4,
 5,
 6,
 7,
 8
 ],
 "nextpage": 2,
 "orderby": "",
 "pagenum": 1,
 "pagesize": 10,
 "pages": 102,
 "prepage": 0,
 "size": 10,
 "startrow": 1,
 "total": 1012
 },
 "message": "success"
 }

當訪問http://127.0.0.1:8079/zeus/user?format=xls 或者http://127.0.0.1:8079/zeus/user.xls

如下效果

SpringBoot中的內容協商器圖解

SpringBoot中的內容協商器圖解

由于這邊的數據和查詢有關 因此我們可以這樣操作http://127.0.0.1:8079/zeus/user.xls?pagesize=1000 輕而易舉實現了查詢結果xls化!

SpringBoot中的內容協商器圖解

SpringBoot中的內容協商器圖解

總結

以上所述是小編給大家介紹的springboot中的內容協商器圖解,希望對大家有所幫助,如果大家有任何疑問請給我留言,小編會及時回復大家的。在此也非常感謝大家對服務器之家網站的支持!

原文鏈接:http://www.jianshu.com/p/f7b257585d9a

延伸 · 閱讀

精彩推薦
主站蜘蛛池模板: 2021国产麻豆剧传媒新片 | 天天狠天天天天透在线 | cosplay 极品videos | 国产精品国语自产拍在线观看 | 日本免费三片在线观看 | 好男人资源在线观看免费的 | 欧美国产在线观看 | 国产一区二 | 亚洲国产精品久久精品成人网站 | 91夜色视频 | 11 13加污女qq看他下面 | 日本手机在线 | 国产精品麻豆久久99 | 国产在线视频在线观看 | 免费视频 | 亚洲国产精品综合久久网络 | 桥本有菜作品在线 | 午夜成私人影院在线观看 | 亚洲一级片在线播放 | 成人啪精品视频免费网站 | 99亚洲视频 | 腿交hd | 国产精品思瑞在线观看 | 明星乱淫 | 506070老熟肥妇bbwxx视频 500第一精品 | 性奶乳妇| 国产一区二区三区在线 | 午夜影视在线观看 | 91美女在线观看 | 韩国三级在线观看 完整版 韩国三级视频网站 | 欧美丝袜foot job | 小小水蜜桃3视频在线观看 小鸟酱喷水 | 男生的j桶女人屁免费视频 男生操男生 | 国产一区在线免费观看 | 爱福利一区二区 | 亚洲AVAV天堂AV在线网爱情 | 久久久久久久国产精品视频 | 亚洲一卡2卡三卡4卡5卡组 | 我们中文在线观看免费完整版 | 91精品久久国产青草 | 欧美精品一线二线大片 |