質問編集履歴
1
import文の追加と文字数制限に伴うTop.controller,html文の移動
title
CHANGED
@@ -1,1 +1,1 @@
|
|
1
|
-
【Spring Security】emailとpasswordでログイン認証を行う
|
1
|
+
【Spring Security】emailとpasswordでログイン認証を行うpart1
|
body
CHANGED
@@ -7,6 +7,15 @@
|
|
7
7
|
### 該当のソースコード
|
8
8
|
|
9
9
|
```Account
|
10
|
+
|
11
|
+
package com.example.demo.entity;
|
12
|
+
import org.springframework.security.core.GrantedAuthority;
|
13
|
+
import org.springframework.security.core.userdetails.UserDetails;
|
14
|
+
import javax.persistence.*;
|
15
|
+
import java.sql.Timestamp;
|
16
|
+
import java.util.Collection;
|
17
|
+
import java.util.Date;
|
18
|
+
|
10
19
|
@Entity
|
11
20
|
@Table(name = "accounts")
|
12
21
|
public class Account implements UserDetails {
|
@@ -103,6 +112,14 @@
|
|
103
112
|
```
|
104
113
|
|
105
114
|
```AccountRepository
|
115
|
+
package com.example.demo.entity;
|
116
|
+
|
117
|
+
import org.springframework.data.jpa.repository.JpaRepository;
|
118
|
+
import org.springframework.data.jpa.repository.JpaSpecificationExecutor;
|
119
|
+
import org.springframework.data.jpa.repository.Query;
|
120
|
+
import org.springframework.data.repository.query.Param;
|
121
|
+
|
122
|
+
import java.util.List;
|
106
123
|
public interface AccountRepository extends JpaRepository<Account, Integer>, JpaSpecificationExecutor<Account> {
|
107
124
|
|
108
125
|
@Query(value = "SELECT * FROM accounts WHERE account_email = :account_email AND account_delete_flag = 0", nativeQuery = true)
|
@@ -130,6 +147,21 @@
|
|
130
147
|
```
|
131
148
|
|
132
149
|
```WebSecurityConfig
|
150
|
+
package com.example.demo.config;
|
151
|
+
|
152
|
+
import com.example.demo.service.JpaUserDetailsServiceImpl;
|
153
|
+
import org.springframework.beans.factory.annotation.Autowired;
|
154
|
+
import org.springframework.context.annotation.Bean;
|
155
|
+
import org.springframework.context.annotation.Configuration;
|
156
|
+
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
|
157
|
+
import org.springframework.security.config.annotation.authentication.configuration.GlobalAuthenticationConfigurerAdapter;
|
158
|
+
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
|
159
|
+
import org.springframework.security.config.annotation.web.builders.WebSecurity;
|
160
|
+
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
|
161
|
+
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
|
162
|
+
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
|
163
|
+
import org.springframework.security.crypto.password.PasswordEncoder;
|
164
|
+
|
133
165
|
@Configuration
|
134
166
|
@EnableWebSecurity
|
135
167
|
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
|
@@ -198,6 +230,16 @@
|
|
198
230
|
```
|
199
231
|
|
200
232
|
```JpaUserDetailsServiceImpl
|
233
|
+
package com.example.demo.service;
|
234
|
+
import com.example.demo.entity.Account;
|
235
|
+
import com.example.demo.entity.AccountRepository;
|
236
|
+
import org.springframework.beans.factory.annotation.Autowired;
|
237
|
+
import org.springframework.security.core.userdetails.UserDetails;
|
238
|
+
import org.springframework.security.core.userdetails.UserDetailsService;
|
239
|
+
import org.springframework.security.core.userdetails.UsernameNotFoundException;
|
240
|
+
import org.springframework.stereotype.Component;
|
241
|
+
import org.springframework.transaction.annotation.Transactional;
|
242
|
+
import java.util.Objects;
|
201
243
|
@Component
|
202
244
|
@Transactional
|
203
245
|
public class JpaUserDetailsServiceImpl implements UserDetailsService {
|
@@ -222,101 +264,7 @@
|
|
222
264
|
|
223
265
|
```
|
224
266
|
|
225
|
-
```TopController
|
226
267
|
|
227
|
-
@Controller
|
228
|
-
@RequestMapping("/top")
|
229
|
-
public class TopController {
|
230
|
-
|
231
|
-
/**トップサービス*/
|
232
|
-
private final TopService service;
|
233
|
-
/** HTTPセッション */
|
234
|
-
private final HttpSession session;
|
235
|
-
/** セッションキー(ログインユーザのアカウント) */
|
236
|
-
private static final String SESSION_FORM_ID = "account";
|
237
|
-
|
238
|
-
/** コード値 */
|
239
|
-
|
240
|
-
@Autowired
|
241
|
-
public TopController(TopService topService, HttpSession session) {
|
242
|
-
this.service = topService;
|
243
|
-
this.session = session;
|
244
|
-
|
245
|
-
}
|
246
|
-
|
247
|
-
/**
|
248
|
-
* ログイン成功時処理。
|
249
|
-
*
|
250
|
-
* @return Path
|
251
|
-
*/
|
252
|
-
@RequestMapping(value = "loginSuccess")
|
253
|
-
public String loginSuccess() {
|
254
|
-
return "redirect:/top";
|
255
|
-
}
|
256
|
-
|
257
|
-
/**
|
258
|
-
* トップ画面表示。
|
259
|
-
*
|
260
|
-
* @param account 認証されたアカウント
|
261
|
-
* @param model モデル
|
262
|
-
* @return Path
|
263
|
-
*/
|
264
|
-
@RequestMapping(value = "")
|
265
|
-
public String init(@AuthenticationPrincipal Account account, Model model) {
|
266
|
-
// 初回のアクセスなら、アカウントを検索してセッションに格納する
|
267
|
-
if (Objects.isNull(session.getAttribute(SESSION_FORM_ID))) {
|
268
|
-
Account sessionAccount = service.getAccountById(account.getAccountId());
|
269
|
-
session.setAttribute(SESSION_FORM_ID, sessionAccount);
|
270
|
-
}
|
271
|
-
|
272
|
-
return "top";
|
273
|
-
}
|
274
|
-
}
|
275
|
-
```
|
276
|
-
|
277
|
-
```login
|
278
|
-
<!DOCTYPE html>
|
279
|
-
<html xmlns:th="http://www.thymeleaf.org">
|
280
|
-
<head xmlns:th="http://www.w3.org/1999/xhtml">
|
281
|
-
<meta charset="UTF-8">
|
282
|
-
<title>Login</title>
|
283
|
-
</head>
|
284
|
-
<body class="body-background">
|
285
|
-
<div>
|
286
|
-
<nav th:replace="nav"></nav>
|
287
|
-
<div class="container">
|
288
|
-
<div class="row justify-content-center">
|
289
|
-
<div class="col-6">
|
290
|
-
<div class="card bg-transparent border-secondary">
|
291
|
-
<div class="card-body">
|
292
|
-
<form class="col-8 offset-2" id="login_form" method="post" th:action="@{'/login'}">
|
293
|
-
<fieldset>
|
294
|
-
<div class="form-group required">
|
295
|
-
<input type="text" name="login_id" id="login_id" class="form-control" placeholder="Email" required/>
|
296
|
-
</div>
|
297
|
-
<div class="form-group required">
|
298
|
-
<input type="password" name="login_password" id="login_password" class="form-control" placeholder="Password" required/>
|
299
|
-
</div>
|
300
|
-
<div class="form-group col-6 offset-3 margin-bottom">
|
301
|
-
<input type="submit" value="Login"
|
302
|
-
class="submit-button btn btn-block center-block bg-custom3"/>
|
303
|
-
</div>
|
304
|
-
</fieldset>
|
305
|
-
</form>
|
306
|
-
<p id="signup">or
|
307
|
-
<a th:href="@{'/account/register/init'}">Sign up</a>
|
308
|
-
</p>
|
309
|
-
</div>
|
310
|
-
</div>
|
311
|
-
</div>
|
312
|
-
</div>
|
313
|
-
</div>
|
314
|
-
</div>
|
315
|
-
</div>
|
316
|
-
</body>
|
317
|
-
</html>
|
318
|
-
```
|
319
|
-
|
320
268
|
### 試したこと
|
321
269
|
1. WebSecurityConfigのfailureUrlをコメントアウト
|
322
270
|
→依然ログイン失敗、URLに/login?errorが表示される
|