質問編集履歴

1

実際に書いたコードを追記します

2020/06/21 23:55

投稿

kachikata96
kachikata96

スコア28

test CHANGED
File without changes
test CHANGED
@@ -27,3 +27,773 @@
27
27
  まだ、springの理解が浅く支離滅裂な質問になってしまい申し訳ありませんが
28
28
 
29
29
  考えられる原因を教えていただけたら幸いです。
30
+
31
+
32
+
33
+ ```java
34
+
35
+ //REST用のサービスクラス
36
+
37
+
38
+
39
+ package com.example.demo.login.domain.service;
40
+
41
+
42
+
43
+ import java.util.List;
44
+
45
+
46
+
47
+ import com.example.demo.login.domain.model.User;
48
+
49
+
50
+
51
+ public interface RestService {
52
+
53
+
54
+
55
+ //1件登録用メソッド
56
+
57
+ public boolean insert(User user);
58
+
59
+
60
+
61
+ //1件検索用メソッド
62
+
63
+ public User selectOne(String userId);
64
+
65
+
66
+
67
+ //全件検索用メソッド
68
+
69
+ public List<User> selectMany();
70
+
71
+
72
+
73
+ //1件更新用メソッド
74
+
75
+ public boolean update(User user);
76
+
77
+
78
+
79
+ //1件削除用メソッド
80
+
81
+ public boolean delete(String userId);
82
+
83
+ }
84
+
85
+ ```
86
+
87
+
88
+
89
+ ```java
90
+
91
+ //JDBCを使うクラス
92
+
93
+
94
+
95
+ package com.example.demo.login.domain.service.jdbc;
96
+
97
+
98
+
99
+ import java.util.List;
100
+
101
+
102
+
103
+ import org.springframework.beans.factory.annotation.Autowired;
104
+
105
+ import org.springframework.beans.factory.annotation.Qualifier;
106
+
107
+ import org.springframework.stereotype.Service;
108
+
109
+ import org.springframework.transaction.annotation.Transactional;
110
+
111
+
112
+
113
+ import com.example.demo.login.domain.model.User;
114
+
115
+ import com.example.demo.login.domain.repository.UserDao;
116
+
117
+ import com.example.demo.login.domain.service.RestService;
118
+
119
+
120
+
121
+ @Transactional
122
+
123
+ @Service
124
+
125
+ public class RestServiceJdbcImpl implements RestService {
126
+
127
+
128
+
129
+ @Autowired
130
+
131
+ @Qualifier("UserDaoJdbcImpl")
132
+
133
+ UserDao dao;
134
+
135
+
136
+
137
+ //1件登録用メソッド
138
+
139
+ @Override
140
+
141
+ public boolean insert(User user) {
142
+
143
+
144
+
145
+ int result = dao.insertOne(user);
146
+
147
+
148
+
149
+ if(result == 0) {
150
+
151
+
152
+
153
+ return false;
154
+
155
+
156
+
157
+ } else {
158
+
159
+
160
+
161
+ return true;
162
+
163
+
164
+
165
+ }
166
+
167
+ }
168
+
169
+
170
+
171
+ //1件検索用メソッド
172
+
173
+ @Override
174
+
175
+ public User selectOne(String userId) {
176
+
177
+ return dao.selectOne(userId);
178
+
179
+ }
180
+
181
+
182
+
183
+ //全件検索用メソッド
184
+
185
+ @Override
186
+
187
+ public List<User> selectMany() {
188
+
189
+ return dao.selectMany();
190
+
191
+ }
192
+
193
+
194
+
195
+ //1件更新用メソッド
196
+
197
+ @Override
198
+
199
+ public boolean update(User user) {
200
+
201
+
202
+
203
+ int result = dao.updateOne(user);
204
+
205
+
206
+
207
+ if(result == 0) {
208
+
209
+
210
+
211
+ return false;
212
+
213
+
214
+
215
+ } else {
216
+
217
+
218
+
219
+ return true;
220
+
221
+
222
+
223
+ }
224
+
225
+ }
226
+
227
+
228
+
229
+ //1件削除用メソッド
230
+
231
+ @Override
232
+
233
+ public boolean delete(String userId) {
234
+
235
+
236
+
237
+ int result = dao.deleteOne(userId);
238
+
239
+
240
+
241
+ if(result == 0) {
242
+
243
+
244
+
245
+ return false;
246
+
247
+
248
+
249
+ } else {
250
+
251
+
252
+
253
+ return true;
254
+
255
+
256
+
257
+ }
258
+
259
+ }
260
+
261
+ }
262
+
263
+ ```
264
+
265
+
266
+
267
+ ```java
268
+
269
+ //REST用のコントローラークラス
270
+
271
+
272
+
273
+ package com.example.demo.login.controller;
274
+
275
+
276
+
277
+ import java.util.List;
278
+
279
+
280
+
281
+ import org.springframework.beans.factory.annotation.Autowired;
282
+
283
+ import org.springframework.web.bind.annotation.DeleteMapping;
284
+
285
+ import org.springframework.web.bind.annotation.GetMapping;
286
+
287
+ import org.springframework.web.bind.annotation.PathVariable;
288
+
289
+ import org.springframework.web.bind.annotation.PostMapping;
290
+
291
+ import org.springframework.web.bind.annotation.PutMapping;
292
+
293
+ import org.springframework.web.bind.annotation.RequestBody;
294
+
295
+ import org.springframework.web.bind.annotation.RestController;
296
+
297
+
298
+
299
+ import com.example.demo.login.domain.model.User;
300
+
301
+ import com.example.demo.login.domain.service.RestService;
302
+
303
+
304
+
305
+ @RestController
306
+
307
+ public class UserRestController {
308
+
309
+
310
+
311
+ @Autowired
312
+
313
+ RestService service;
314
+
315
+
316
+
317
+ /**
318
+
319
+ * ユーザー全件取得
320
+
321
+ */
322
+
323
+ @GetMapping("/rest/get")
324
+
325
+ public List<User> getUserMany() {
326
+
327
+
328
+
329
+ // ユーザー全件取得
330
+
331
+ return service.selectMany();
332
+
333
+ }
334
+
335
+
336
+
337
+ /**
338
+
339
+ * ユーザー1件取得
340
+
341
+ */
342
+
343
+ @GetMapping("/rest/get/{id:.+}")
344
+
345
+ public User getUserOne(@PathVariable("id") String userId) {
346
+
347
+
348
+
349
+ // ユーザー1件取得
350
+
351
+ return service.selectOne(userId);
352
+
353
+ }
354
+
355
+
356
+
357
+ /**
358
+
359
+ * ユーザー1件登録
360
+
361
+ */
362
+
363
+ @PostMapping("/rest/insert")
364
+
365
+ public String postUserOne(@RequestBody User user) {
366
+
367
+
368
+
369
+ // ユーザーを1件登録
370
+
371
+ boolean result = service.insert(user);
372
+
373
+
374
+
375
+ String str = "";
376
+
377
+
378
+
379
+ if(result == true) {
380
+
381
+
382
+
383
+ str = "{\"result\":\"ok\"}";
384
+
385
+
386
+
387
+ } else {
388
+
389
+
390
+
391
+ str = "{\"result\":\"error\"}";
392
+
393
+
394
+
395
+ }
396
+
397
+
398
+
399
+ // 結果用の文字列をリターン
400
+
401
+ return str;
402
+
403
+ }
404
+
405
+
406
+
407
+ /**
408
+
409
+ * ユーザー1件登録
410
+
411
+ */
412
+
413
+ @PutMapping("/rest/update")
414
+
415
+ public String putUserOne(@RequestBody User user) {
416
+
417
+
418
+
419
+ // ユーザーを1件登録
420
+
421
+ boolean result = service.update(user);
422
+
423
+
424
+
425
+ String str = "";
426
+
427
+
428
+
429
+ if(result == true) {
430
+
431
+
432
+
433
+ str = "{\"result\":\"ok\"}";
434
+
435
+
436
+
437
+ } else {
438
+
439
+
440
+
441
+ str = "{\"result\":\"error\"}";
442
+
443
+
444
+
445
+ }
446
+
447
+
448
+
449
+ // 結果用の文字列をリターン
450
+
451
+ return str;
452
+
453
+ }
454
+
455
+
456
+
457
+ @DeleteMapping("/rest/delete/{id:.+}")
458
+
459
+ public String deleteUserOne(@PathVariable("id") String userId) {
460
+
461
+
462
+
463
+ // ユーザーを1件削除
464
+
465
+ boolean result = service.delete(userId);
466
+
467
+
468
+
469
+ String str = "";
470
+
471
+
472
+
473
+ if(result == true) {
474
+
475
+
476
+
477
+ str = "{\"result\":\"ok\"}";
478
+
479
+
480
+
481
+ } else {
482
+
483
+
484
+
485
+ str = "{\"result\":\"error\"}";
486
+
487
+
488
+
489
+ }
490
+
491
+
492
+
493
+ // 結果用の文字列をリターン
494
+
495
+ return str;
496
+
497
+ }
498
+
499
+ }
500
+
501
+ ```
502
+
503
+
504
+
505
+ ```java
506
+
507
+ //RESTサービスのみCSRF対策を無効にするためにRequestMatcherを実装したクラス
508
+
509
+
510
+
511
+ package com.example.demo;
512
+
513
+
514
+
515
+ import javax.servlet.http.HttpServletRequest;
516
+
517
+
518
+
519
+ import org.springframework.security.web.util.matcher.AntPathRequestMatcher;
520
+
521
+ import org.springframework.security.web.util.matcher.RequestMatcher;
522
+
523
+
524
+
525
+ public class RestMatcher implements RequestMatcher {
526
+
527
+
528
+
529
+ //マッチャー
530
+
531
+ private AntPathRequestMatcher matcher;
532
+
533
+
534
+
535
+ //コンストラクタ
536
+
537
+ public RestMatcher(String url) {
538
+
539
+ super();
540
+
541
+ matcher = new AntPathRequestMatcher(url);
542
+
543
+ }
544
+
545
+
546
+
547
+ //URLのマッチ条件
548
+
549
+ @Override
550
+
551
+ public boolean matches(HttpServletRequest request) {
552
+
553
+
554
+
555
+ // GETならCSRFのチェックはしない
556
+
557
+ if("GET".equals(request.getMethod()))
558
+
559
+ return false;
560
+
561
+
562
+
563
+ // 特定のURLに該当する場合、CSRFチェックしない
564
+
565
+ if(matcher.matches(request))
566
+
567
+ return false;
568
+
569
+
570
+
571
+ return true;
572
+
573
+ }
574
+
575
+ }
576
+
577
+ ```
578
+
579
+
580
+
581
+ ```java
582
+
583
+ //上記のRequestMatcherを反映させたSecuriryConfigクラス
584
+
585
+
586
+
587
+ package com.example.demo;
588
+
589
+
590
+
591
+ import javax.sql.DataSource;
592
+
593
+
594
+
595
+ import org.springframework.beans.factory.annotation.Autowired;
596
+
597
+ import org.springframework.context.annotation.Bean;
598
+
599
+ import org.springframework.context.annotation.Configuration;
600
+
601
+ import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
602
+
603
+ import org.springframework.security.config.annotation.web.builders.HttpSecurity;
604
+
605
+ import org.springframework.security.config.annotation.web.builders.WebSecurity;
606
+
607
+ import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
608
+
609
+ import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
610
+
611
+ import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
612
+
613
+ import org.springframework.security.crypto.password.PasswordEncoder;
614
+
615
+ import org.springframework.security.web.util.matcher.AntPathRequestMatcher;
616
+
617
+ import org.springframework.security.web.util.matcher.RequestMatcher;
618
+
619
+
620
+
621
+ @EnableWebSecurity
622
+
623
+ @Configuration
624
+
625
+ public class SecurityConfig extends WebSecurityConfigurerAdapter {
626
+
627
+
628
+
629
+ // データソース
630
+
631
+ @Autowired
632
+
633
+ private DataSource dataSource;
634
+
635
+
636
+
637
+ @Bean
638
+
639
+ public PasswordEncoder passwordEncoder() {
640
+
641
+ return new BCryptPasswordEncoder();
642
+
643
+ }
644
+
645
+
646
+
647
+ // ユーザーIDとパスワードを取得するSQL文
648
+
649
+ private static final String USER_SQL = "SELECT"
650
+
651
+ + " user_id,"
652
+
653
+ + " password,"
654
+
655
+ + " true"
656
+
657
+ + " FROM"
658
+
659
+ + " m_user"
660
+
661
+ + " WHERE"
662
+
663
+ + " user_id = ?";
664
+
665
+
666
+
667
+ // ユーザーのロールを取得するSQL文
668
+
669
+ private static final String ROLE_SQL = "SELECT"
670
+
671
+ + " user_id,"
672
+
673
+ + " role"
674
+
675
+ + " FROM"
676
+
677
+ + " m_user"
678
+
679
+ + " WHERE"
680
+
681
+ + " user_id = ?";
682
+
683
+
684
+
685
+ @Override
686
+
687
+ public void configure(WebSecurity web) throws Exception {
688
+
689
+
690
+
691
+ //静的リソースへのアクセスには、セキュリティを適用しない
692
+
693
+ web.ignoring().antMatchers("/webjars/∗∗", "/css/∗∗");
694
+
695
+ }
696
+
697
+
698
+
699
+ @Override
700
+
701
+ protected void configure(HttpSecurity http) throws Exception {
702
+
703
+
704
+
705
+ // ログイン不要ページの設定
706
+
707
+ http
708
+
709
+ .authorizeRequests()
710
+
711
+ .antMatchers("/webjars/**").permitAll() //webjarsへアクセス許可
712
+
713
+ .antMatchers("/css/**").permitAll() //cssへアクセス許可
714
+
715
+ .antMatchers("/login").permitAll() //ログインページは直リンクOK
716
+
717
+ .antMatchers("/signup").permitAll() //ユーザー登録画面は直リンクOK
718
+
719
+ .antMatchers("/rest/**").permitAll() //RESTは直リンクOK
720
+
721
+ .antMatchers("/admin").hasAuthority("ROLE_ADMIN") //アドミンユーザーに許可
722
+
723
+ .anyRequest().authenticated(); //それ以外は直リンク禁止
724
+
725
+
726
+
727
+ //ログイン処理
728
+
729
+ http
730
+
731
+ .formLogin()
732
+
733
+ .loginProcessingUrl("/login") //ログイン処理のパス
734
+
735
+ .loginPage("/login") //ログインページの指定
736
+
737
+ .failureUrl("/login") //ログイン失敗時の遷移先
738
+
739
+ .usernameParameter("userId") //ログインページのユーザーID
740
+
741
+ .passwordParameter("password") //ログインページのパスワード
742
+
743
+ .defaultSuccessUrl("/home", true); //ログイン成功後の遷移先
744
+
745
+
746
+
747
+ //ログアウト処理
748
+
749
+ http
750
+
751
+ .logout()
752
+
753
+ .logoutRequestMatcher(new AntPathRequestMatcher("/logout")) //
754
+
755
+ .logoutUrl("/logout") //ログアウトのURL
756
+
757
+ .logoutSuccessUrl("/login"); //ログアウト成功後のURL
758
+
759
+
760
+
761
+ //CSRFを無効にするURLを設定
762
+
763
+ RequestMatcher csrfMatcher = new RestMatcher("/rest/**");
764
+
765
+
766
+
767
+ //RESTのみCSRF対策を無効に設定
768
+
769
+ http.csrf().requireCsrfProtectionMatcher(csrfMatcher);
770
+
771
+ }
772
+
773
+
774
+
775
+ @Override
776
+
777
+ protected void configure(AuthenticationManagerBuilder auth) throws Exception {
778
+
779
+
780
+
781
+ // ログイン処理時のユーザー情報を、DBから取得する
782
+
783
+ auth.jdbcAuthentication()
784
+
785
+ .dataSource(dataSource)
786
+
787
+ .usersByUsernameQuery(USER_SQL)
788
+
789
+ .authoritiesByUsernameQuery(ROLE_SQL)
790
+
791
+ .passwordEncoder(passwordEncoder());
792
+
793
+ }
794
+
795
+ }
796
+
797
+
798
+
799
+ ```