【Java】Enum

定義

Enums.java

public class Enums {
    public static enum Sex {
        MALE("1","MALE","男","1"),
        FEMALE("2","FEMALE","女","2"),
        OTHER("3","OTHER","その他","3");

        private Sex(String code, String ename, String jname, String sortOrder) {
            this.code = code;
            this.ename = ename;
            this.jname = jname;
            this.sortOrder = sortOrder;
        }
        private final String code;
        private final String ename;
        private final String jname;
        private final String sortOrder;

        public String getCode() {return code;}
        public String getEname() {return ename;}
        public String getJname() {return jname;}
        public String getSortOrder() {return sortOrder;}

    }
}

使用方法

        Enums.Sex.MALE.getCode();       // 1
        Enums.Sex.MALE.getEname();      // MALE
        Enums.Sex.MALE.getJname();      // 男
        Enums.Sex.MALE.getSortOrder();  // 1

【Spring】基礎知識

バージョンの確認・変更

pom.xmlから確認・変更可能
※例はMaven

  <properties>
    <java-version>1.8</java-version>
    <org.springframework-version>5.3.0</org.springframework-version>
    <org.aspectj-version>1.6.10</org.aspectj-version>
    <org.slf4j-version>1.6.6</org.slf4j-version>
  </properties>
  <dependencies>
    <!-- Spring -->
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-context</artifactId>
      <version>${org.springframework-version}</version>
      <exclusions>
        <!-- Exclude Commons Logging in favor of SLF4j -->
        <exclusion>
          <groupId>commons-logging</groupId>
          <artifactId>commons-logging</artifactId>
         </exclusion>
      </exclusions>
    </dependency>
    <dependency>
      <groupId>org.springframework</groupId>
      <artifactId>spring-webmvc</artifactId>
      <version>${org.springframework-version}</version>
    </dependency>
    <!-- JDBC -->
    <dependency>
        <groupId>org.springframework</groupId>
        <artifactId>spring-jdbc</artifactId>
        <version>${org.springframework-version}</version>
    </dependency>
  </dependencies>

文字化け回避

web.xmlに追記する

  <filter>
    <filter-name>characterEncodingFilter</filter-name>
      <filter-class>
        org.springframework.web.filter.CharacterEncodingFilter
      </filter-class>
    <init-param>
      <param-name>encoding</param-name>
      <param-value>UTF-8</param-value>
    </init-param>
    <init-param>
      <param-name>forceEncoding</param-name>
      <param-value>true</param-value>
    </init-param>
  </filter>
  <filter-mapping>
    <filter-name>characterEncodingFilter</filter-name>
    <url-pattern>/*</url-pattern>
  </filter-mapping>

コンテキストルート

コンテキストルートとはウェブアプリケーションにおける最上位のパス(URL)。

確認方法


DI

SpringはDIを使用している。
インスタンスはシングルトンで使いまわしされるためメンバ変数が共有される。
メンバ変数を使用している場合は値が初期化されないため注意する。
詳しくは下の記事に記載
【Spring】DI - アルパカノフン

indexファイル

コンテキストルートのURLで開くファイル。
WEB-INFの配下に配置する。
例)http://localhost:8080/demo/


web.xmlで定義されている

画面遷移

コントローラー

・@RequestMappingとURLが紐づく
・returnに開くjsp名を指定する
例.http://localhost:8080/demo/offer_initDisplay

@Controller
public class OfferController {

    @RequestMapping(value = "offer_initDisplay", method = RequestMethod.GET)
    public String initDisplay(Model model) {
        // webapp/WEB-INF/views/offer/offerInit.jspを開く
        return "offer/offerInit";
    }
}

【応用】
・クラスに@RequestMappingをつける
・@GetMapping/@PostMappingを使用する(Spring 4.3以降)
例.http://localhost:8080/demo/offer/offer_initDisplay

@Controller
@RequestMapping("offer")
public class OfferController {

    @GetMapping("offer_initDisplay")
    public String initDisplay(Model model) {
        return "offer/offerInit";
    }
    @PostMapping("offer_confirm")
    public String confirm(Model model) {
        return "offer/confirmOffer";
    }
}
jsp

servlet-context.xmljspの場所を指定する

  <beans:bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
    <beans:property name="prefix" value="/WEB-INF/views/" />
    <beans:property name="suffix" value=".jsp" />
  </beans:bean>

Controller↔jsp間の値の受け渡し(modelAttributeを使用)

modelAttributeを使用するとFormの値をFormでまとめて取得することができる

modelAttributeを使用したjspを呼び出すコントローラー

jspのformでmodelAttributeを使用している場合、modelにつめて渡す必要がある

@Controller
@RequestMapping("offer")
public class OfferController {

    @GetMapping("offer_initDisplay")
    public String initDisplay(Model model) {
        // jspのmodelAttributeに渡す必要がある
        model.addAttribute("offerForm", new OfferForm());
        return "offer/offer";
    }
}
jspの値渡し

・modelAttributeで格納先のFormを指定
・formactionで遷移先のコントローラーを指定

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<%@ taglib prefix="form" uri="http://www.springframework.org/tags/form" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
</head>
<body>
<form:form modelAttribute="offerForm" method="post">
    <label>ユーザーID:</label>
    <form:input path="userId"/><br>
    <label>名前:</label>
    <form:input path="name"/><br>

    <input type="submit" value="確認へ進む" formaction="offer_confirm"/>

    <input type="hidden" name="hiddenItem" value="hiddenValue">
</form:form>
</body>
</html>
コントローラーでの受け渡し

・@ModelAttributeでjspのformを受け取ることができる
・引数でjsp内のpathやnameを指定することでも受け取ることができる
jspに渡す内容はmodelにつめる(model.addAttribute)

@Controller
@RequestMapping("offer")
public class ConfirmOffer {

    @PostMapping("offer_confirm")
    public String confirm(Model model,
            @ModelAttribute("offerForm") OfferForm form, // formの値を取得
            @RequestParam(name="userId") String id, // これでも取得可能
            String hiddenItem    // これでも取得可能
            ) {

        System.out.println(id);
        System.out.println(hiddenItem);

        // jspに値を渡す
        model.addAttribute("offerForm", form);

        return "offer/confirmOffer";
    }
}
jspの値受け取り

・コントローラーのmodelにつめた値を使用できる

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
</head>
<body >
${offerForm.userId}<br>
${offerForm.name}
</body>
</html>
画面イメージ


文字化けする場合は上記の「文字化け回避」の設定が必要
格納先がString型以外の場合、文字列を入力した場合はエラーになるので注意

Controller↔jsp間の値の受け渡し(modelAttributeを使用しない)

jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<%@ taglib prefix="form" uri="http://www.springframework.org/tags/form" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
</head>
<body>
<form method="post">
    <label>ユーザーID:</label>
    <input type="text" name="userId"/><br>
    <label>名前:</label>
    <input type="text" name="name"/><br>
    <input type="submit" value="確認へ進む" formaction="offer_confirm"/>
</form>
</body>
</html>

【controller】
@RequestParamや引数を使用して値を受け取る

@Controller
@RequestMapping("offer")
public class ConfirmOffer {

    @PostMapping("offer_confirm")
    public String confirm(Model model,
            @RequestParam(name="userId") String id,
            @RequestParam(name="name") String name,
            String userId) { // @RequestParamなしでも取得可能。jspのnameと同じ名前にすること

        model.addAttribute("userId", id);
        model.addAttribute("name", name);

        return "offer/confirmOffer";
    }
}

【Spring】コンテキストパス変更

コンテキストパスとは


コンテキストルートとは


変更方法

①プロジェクトを右クリックしてプロパティを開く
②Webプロジェクトの設定を開き、値を変更する

③サーバからリソースを削除し、再度追加する

④コンテキストパスが変更されていることを確認

【SQL】複雑な問合わせ

指定した値をすべて含むレコードを検索

bが1~5を含むレコードのaを取得

SELECT a FROM t1 WHERE b IN (1,2,3,4,5) 
  GROUP BY a HAVING CONST(DISTINCT b) = 5

最大の値を持つレコードをキーごとに抽出

group by でキーを指定するのがポイント

SELECT a.* FROM 社員マスタ a 
  INNER JOIN ( 
    SELECT 部署コード, MAX(入社年月日) MAX_入社年月日 FROM 社員マスタ GROUP BY 部署コード
  ) b 
    ON a.部署コード = b.部署コード 
    AND a.入社年月日 = b.MAX_入社年月日

【例】"部署コードごと"に入社年月日が最大のレコードを抽出
(抽出前)

社員コード 氏名 生年月日 住所 電話番号 部署コード 入社年月日
0001 高橋 一生 1988/11/09 大阪府大阪市北区池田町1-1 080-1111-1111 001 2001/04/01
0002 高橋 二生 1989/12/02 大阪府大阪市北区池田町1-1 080-1111-2222 001 2002/04/01
0003 検証 太郎 1999/01/01 大阪府大阪市 090-1111-2222 002 2010/01/01
0004 検証 次郎 1999/01/01 大阪府大阪市 090-1111-2222 002 2011/01/01

(抽出後)

社員コード 氏名 生年月日 住所 電話番号 部署コード 入社年月日
0002 高橋 二生 1989/12/02 大阪府大阪市北区池田町1-1 080-1111-2222 001 2002/04/01
0004 検証 次郎 1999/01/01 大阪府大阪市 090-1111-2222 002 2011/01/01

最大の値を持つレコードを抽出

WHEREのサブクエリを使用するのがポイント

SELECT * FROM 社員マスタ
  WHERE 入社年月日 = ( 
    SELECT MAX(入社年月日) FROM 社員マスタ
  )  

【例】入社年月日が最大のレコードを抽出
(抽出前)

社員コード 氏名 生年月日 住所 電話番号 部署コード 入社年月日
0003 検証 太郎 1999/01/01 大阪府大阪市 090-1111-2222 002 2010/01/01
0004 検証 次郎 1999/01/01 大阪府大阪市 090-1111-2222 002 2011/01/01

(抽出後)

社員コード 氏名 生年月日 住所 電話番号 部署コード 入社年月日
0004 検証 次郎 1999/01/01 大阪府大阪市 090-1111-2222 002 2011/01/01

ツール類

チャット

Teams


Slack


SSH

Tera Term

特徴:コマンド式。バッチの実行でよく使う。

ファイル送受信

サーバとのファイルのやり取りで主に使用

WinSCP

特徴:画面から直感的に操作可能

FileZilla

特徴:画面から直感的に操作可能

タスク管理

Jira


DB

SQL Developer

ラクル製

Object Browser

有料

エディター

サクラエディタ

ソートやマージ、Grepが便利

フォルダ管理

Tablacus Explorer

エクスプローラーをタブで開くことができる

CSVエディタ

Cassava Editor

区切り文字や囲み文字をオプションで指定できるのが便利

【Spring】アノテーション

カッコはアノテーションを記述する場所

@Component(クラス)

SpringDIコンテナにbeanとして登録したいクラスへ付与する。
コンポーネントスキャンの対象になっている必要あり
DIとして使用する場合、シングルトンになるため、メンバ変数を使用している場合は共有されることを注意。(回避方法あり)

@Component
public class OfferComponent {
    ...
}

コンポーネントスキャン対象の設定方法】
spring-mvc.xml(servlet-context.xml)に下記を記載する
※設定方法は他にも方法あり

</beans><context:component-scan base-package="jp.co.demo" /></beans>

@Controller(クラス)

@Componentと基本的には同じ働きをするが、SpringMVCでControllerの役割となるクラスに付与する。

@Controller
public class OfferController {
    ...
}

@Service(クラス)

@Componentと基本的には同じ働きをするが、Service層(ビジネスロジック等)を対象としている。

@Service
public class OfferService {
    ...
}

@Repository(クラス)

@Componentと基本的には同じ働きをするが、Persistence層(DAO等のDBアクセスを行うクラス)を対象としている。

@Repository
public class OfferRepository {
    ...
}

@RestController(クラス)

REST API 用の Controller クラス(Viewに遷移せず、メソッドの戻り値をそのままレスポンスとして返す)に使用する。

@RestController
public class RestController {
    ...
}

@RequestMapping(クラス、メソッド)

URLリクエストとクラス、メソッドのマッピングを行う。

【属性】

@RequestMapping(value="/test", method=RequestMethod.GET, headers="Accept=application/*", params="id=002")

// 省略してvalueのみ指定可能(POSTになる)
@RequestMapping("/test")
value コンテキストルートからのパスを記載する。複数指定可能。ワイルドカード使用可能。
method GET、POST等を指定する。複数指定可能。省略時はPOSTになる。
headers HTTPヘッダ名のみ指定されている場合は、そのヘッダが存在するかどうかでマッチの判定。ヘッダ名と値が指定されている場合は、ヘッダにその値が設定されているかどうかでマッチの判定。
params リクエストパラメーターを指定する。

【使用例】

@Controller
// コンテキストルート/offerでこのクラスを指定
@RequestMapping("/offer")
public class OfferController {

    // コンテキストルート/offer/offer_initDisplayでこのメソッドを指定
    @RequestMapping("/offer_initDisplay")
    public String initDisplay(Model model) {
        return "offer";
    }

    // URLを複数指定可能、ワイルドカード使用可能
    // ?は1文字、*は0文字以上(/offer2/aとか不可)、**は0文字以上(/offer3/aとか可能)
    @RequestMapping(value = {"/offer1?","/offer2*", "/offer3/**"})
    public String initDisplay2(Model model) {
        return "offer";
    }

    // methodは複数指定可能
    @RequestMapping(value="/offer4", method={RequestMethod.GET, RequestMethod.POST})
    public String initDisplay3(Model model) {
        return "offerConfirm";
    }

    // paramsでリクエストの値を指定可能
    @RequestMapping(value="offer_confirm", params="userId=1")
    public String confirm(Model model) {
        return "offerConfirm";
    }

    // paramsは複数指定可能
    @RequestMapping(value="offer_confirm", params={"userId=1", "name=あ"})
    public String confirm2(Model model) {
        return "offerConfirm";
    }
}

@PostMapping/@GetMapping(メソッド)

※Spring 4.3以降
RequestMappingとほぼ同様。メソッドが省略できる。
methodがPOSTの場合:PostMapping
methodがGETの場合:GetMapping

@Controller
@RequestMapping("/offer")
public class OfferController {

    @PostMapping("/offer_initDisplay")
    public String initDisplay(Model model) {
        return "offer";
    }

    @GetMapping(value = {"/offer1?","/offer2*", "/offer3/**"})
    public String initDisplay2(Model model) {
        return "offer";
    }
}

@ModelAttribute(メソッドの引数、メソッド)

メソッドの引数:画面(jsp)からフォームの値を受け取り、Modelに格納する。画面(jsp)のModelAttributeと紐づける必要あり。
メソッド:RequestMappingの前に実行される。Modelに格納する。

【メソッドの引数】
@ModelAttribute("{受け取るformの名前}") {格納する型} {格納する変数名}

@Controller
public class ConfirmOffer {

    @PostMapping("offer_confirm")
    public String confirm(Model model,
            @ModelAttribute("offerForm") OfferForm form) {

        // 変更すると変更した値が画面に渡される
        form.setName("値を変更");

        // Modelに格納済みのため、model.addAttribute不要で画面で使用可能
//        model.addAttribute("offerForm", form);
        return "offer/confirmOffer";
    }
}

画面(jsp)
modelAttributeでControllerの@ModelAttributeの値と紐づける必要あり

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<%@ taglib prefix="form" uri="http://www.springframework.org/tags/form" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
</head>
<body>
<form:form modelAttribute="offerForm">
    <label>ユーザーID:</label>
    <form:input path="userId"/><br>
    <label>名前:</label>
    <form:input path="name"/><br>
    <input type="submit" value="確認へ進む" formaction="offer_confirm"/>
</form:form>
</body>
</html>

【メソッド】
@ModelAttribute("{modelに格納する変数名}")

@Controller
public class ConfirmOffer {

    // RequestMappingの前に実行される。値をModelにセットする。メソッド名は不問
    @ModelAttribute("aiueo")
    private String setupForm() {
        return "あいうえお";
    }

    @RequestMapping("offer_confirm")
    public String confirm(Model model) {

        // Modelの変数を使用
        System.out.println(model.getAttribute("aiueo"));
        return "offer/confirmOffer";
    }
}

@PathVariable(メソッドの引数)

URLに含まれる動的なパラメータを受け取る。
【属性】

@PathVariable(name="id", required=true) String userId

// 省略時
@PathVariable("id") String userId
name URLに含まれるパラメータに紐づく
required true:必須、false:必須でない。省略時はtrue:必須

使用例

@Controller
public class OfferController {

    @GetMapping("/offer_initDisplay/sample_{id}")
    public String initDisplay(Model model,
            @PathVariable("id") String userId) {

        // 使用
        System.out.println(userId);

        return "offer/offer";
    }
}

@RequestParam(メソッドの引数)

GETやPOSTのパラメータの値を受け取る。
【属性】

@RequestParam(name="id", required = true, defaultValue="default") String userId)

// 省略時
@RequestParam("id") String userId
name URLに含まれるパラメータに紐づく
required true:必須、false:必須でない。省略時はtrue:必須。defaultValueがある場合はtrueでもエラーにならない
defaultValue リクエストパラメータが指定されなかった時のデフォルト値を指定

【使用例】
・GETの場合
URLのパラメータを取得する
http://localhost:8080/demo/offer_initDisplay?id=sample

@Controller
public class OfferController {

    @GetMapping("/offer_initDisplay")
    public String initDisplay(Model model,
            @RequestParam(name="id") String userId) {

        System.out.println(userId);

        return "offer/offer";
    }
}

・POSTの場合
formで送信された値を取得する

@Controller
public class ConfirmOffer {

    @PostMapping("offer_confirm")
    public String confirm(Model model,
            @RequestParam(name="userId") String id,
            @RequestParam(name="name") String name,
            String userId) { // @RequestParamなしでも取得可能

        System.out.println(id);
        System.out.println(name);

        return "offer/confirmOffer";
    }
}

jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<%@ taglib prefix="form" uri="http://www.springframework.org/tags/form" %>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
</head>
<body>
<form method="post">
    <label>ユーザーID:</label>
    <input type="text" name="userId"/><br>
    <label>名前:</label>
    <input type="text" name="name"/><br>
    <input type="submit" value="確認へ進む" formaction="offer_confirm"/>
</form>
</body>
</html>

@Scope(クラス)

インスタンスのスコープ(ライフサイクル)を変更する。
コントローラーやサービスはシングルトン(インスタンスを使いまわす)のため、メンバ変数の共有を防ぐためにrequestやprototypeを指定する。

singleton コンテナに対してインスタンスを1つだけ作成(デフォルト)
prototype 呼び出される毎にインスタンスを作成
request 1回のHTTPリクエスト毎にインスタンスを作成
session HTTPセッション毎にインスタンスを作成
@Controller
@Scope("request")
public class OfferController {
    // メンバ変数
    String sampleName;

    @GetMapping("/offer_initDisplay")
    public String initDisplay(Model model){
        System.out.println(sampleName);    // リクエスト毎にインスタンスが作成されるためnullが表示(共有されない)
        // メンバ変数に代入
        serviceName = "a";
        return "offer";
    }
}

@Autowired(クラス)

DIコンテナからBeanをDIする。(型が一致するクラスをDIする)
newを使ったインスタンス化と同じ。
シングルトンのためメンバ変数を使用している場合は、値が共有されるため注意する。(回避方法あり)

【属性】

@Autowired(required=false)
required true:対象のBeanがDIコンテナにないとエラー、false:DIコンテナになくてもエラーにならない。省略時はtrue。

【使用方法】
【Spring】DI - アルパカノフンに記載

@Qualifier(クラス)

@Autowiredと併用する。
@Autowiredでbean名を指定したい場合に使用する。

@Autowired
@Qualifier("beanName")

@Inject(クラス)

@Autowiredと同じ機能。
javaアノテーション

@Resource(クラス)

DIコンテナからBeanをDIする。(名称が一致するクラスをDIする)
javaアノテーション

@Resource(name="beanName")
name bean名を指定する。省略時はフィールド名の名前から指定する。

@Value(フィールド)

主にプロパティファイルの値を入力する際に使用。
【Spring】テクニック - アルパカノフンに記載。

@Transactional(クラス、メソッド)

トランザクションを行う。
【Spring】MyBatis - アルパカノフンに記載。

【Spring】DI

DIとは

インスタンスを共有化して効率を上げる仕組み。→クラスを使うときにnewしない
また、メンバ変数への代入をクラス内で行うのではなく、外部(xmlファイル等)から設定するという考え方。

DIの注意点

@Controllerを付与したControllerクラスや@Serviceを付与したServiceクラスもDI対象でシングルトン。
シングルトンはアプリケーションで1つのインスタンスを共有するため、メンバ変数が共有されてしまう。
※ローカル変数は対象外

@Controller
public class OfferController {
    // メンバ変数
    String sampleName;

    @GetMapping("/offer_initDisplay")
    public String initDisplay(Model model){
        System.out.println(sampleName);    // 初期表示時はnullだが以降は「a」が表示
        // メンバ変数に代入
        serviceName = "a";
        return "offer";
    }
}

メンバ変数の共有化を防ぐ方法は
1.メンバ変数を使用しない
2.@Scopeアノテーションを使用する(requestまたはprototype)
※Controllerの場合request、Serviceの場合prototypeで良い

@Controller
@Scope("request")
public class OfferController {
    // メンバ変数
    String sampleName;

    @GetMapping("/offer_initDisplay")
    public String initDisplay(Model model){
        System.out.println(sampleName);    // リクエスト毎にインスタンスが作成されるためnull(共有されない)
        // メンバ変数に代入
        serviceName = "a";
        return "offer";
    }
}

使用方法1.アノテーションを使用(Webアプリの場合)

アノテーションを付与し、コンポーネントスキャンすることでDIコンテナに登録する。
※Bean登録するクラスはコンストラクタの使用不可っぽい
※Bean登録するクラスがメンバ変数を使用している場合、@Scope("prototype")でメンバ変数が共有されることを防ぐこと。DIはシングルトンのためメンバ変数が共有されることを覚えておく。

Beanの登録

コンポーネンストキャンの対象にする
servlet-context.xml(spring-mvc.xml)

<beans>
  ・・・
  <!-- このパスの配下がコンポーネントスキャンの対象となる -->
  <context:component-scan base-package="jp.co.demo" />
  ・・・
</beans>

コンポーネントスキャン対象のアノテーション
コンポーネントスキャン対象かつ下記アノテーションがついている場合、自動でBean登録される。

@Controller このアノテーションを付与したコンポーネントでは、クライアントからのリクエスト/レスポンスに関わる処理をする。
@Service ビジネスロジックを実装するコンポーネントであることを表すアノテーション
@Repository データの永続化に関わる処理を提供するコンポーネント。ORMなどを利用して、データのCRUD処理を実装する。
@Component 上記3つに当てはまらないコンポーネント。ユーティリティクラスなどに付与する。
@Configuration クラス宣言の前に記述します。このアノテーションは、このクラスがBeanの設定を行うものであることを示します。Bean設定クラスには常にこれをつけます。
@RestController JSONXML等を返すWebAPI用のコントローラに付与する。
DIの方法1.(コンストラクタインジェクション)

一番オススメされる方法。final化できるのが特徴。

@Controller
@Scope("request")
public class OfferController {

    // コンストラクタインジェクション
    private final OfferService offerService;
    private final BaseOfferService baseOfferService;
    // ※@Autowired省略可能
    @Autowired
    public OfferController(OfferService offerService, BaseOfferService baseOfferService) {
        this.offerService = offerService;
        this.baseOfferService = baseOfferService;
    }

    @GetMapping("/offer_initDisplay")
    public String initDisplay(Model model) {
        offerService.setServiceName("a");
        return "offer/offer";
    }
}
DIの方法2.(セッターインジェクション)

DIするクラスごとにセッターを増やす必要がある。

@Controller
@Scope("request")
public class OfferController {

    // セッターインジェクション
    private OfferService offerService;
    private BaseOfferService baseOfferService;

    @Autowired
    public void setOfferService(OfferService offerService) {
        this.offerService = offerService;
    }
    @Autowired
    public void setBaseOfferService(BaseOfferService baseOfferService) {
        this.baseOfferService = baseOfferService;
    }

    @GetMapping("/offer_initDisplay")
    public String initDisplay(Model model) {
        offerService.setServiceName("a");
        return "offer/offer";
    }
}
DIの方法3.(フィールドインジェクション)

一番簡単に書ける。

@Controller
@Scope("request")
public class OfferController {

    // フィールドインジェクション
    @Autowired
    private OfferService offerService;
    @Autowired
    private BaseOfferService baseOfferService;

    @GetMapping("/offer_initDisplay")
    public String initDisplay(Model model) {
        offerService.setServiceName("a");
        return "offer/offer";
    }
}

使用方法2.XMLを使用

Bean登録

XMLにDIコンテナに登録するBean(クラス)を記載する。

xml

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="
        http://www.springframework.org/schema/beans
        http://www.springframework.org/schema/beans/spring-beans.xsd">

    <!-- Beanの登録のみ -->
    <!-- ※初期値の設定を省略したメンバ変数はnullが設定される -->
    <bean id="baseOfferForm" class="jp.co.demo.common.form.BaseOfferForm" />

    <!-- Beanの登録+メンバ変数への初期値を設定(セッターインジェクション) -->
    <!-- ※初期値の設定を省略したメンバ変数はnullが設定される -->
    <bean id="offerForm" class="jp.co.demo.offer.form.OfferForm">
        <property name="name" value="nameの値" />
        <property name="baseOfferForm" ref="baseOfferForm" />    <!-- あらかじめ定義されたbeanIdを使用する場合、refを使用する -->
    </bean>

    <!-- Beanの登録+クラスでコンストラクタを使用してメンバ変数を設定する場合(コンストラクタインジェクション) -->
    <!-- ※typeは型、indexは引数の順番、refはbeanIdを使用する場合 -->
    <bean id="offerService" class="jp.co.demo.offer.service.OfferService">
        <constructor-arg value="引数1つ目の値" type="String" index="0" />
        <constructor-arg ref="offerForm" index="1" />
    </bean>
</beans>

【呼び出し方法1】

public class OfferSample {

    public String initDisplay() {
        ClassPathXmlApplicationContext contxt =
                new ClassPathXmlApplicationContext("beans/serviceBeans.xml");
        // xmlのbeanIDを指定する
        OfferService service = (OfferService)contxt.getBean("offerService");

        System.out.println(service.getServiceName());

        contxt.close();
        return "offer/offer";
    }
}

【呼び出し方法2】
ContextLoaderを使用する。
Beanのファイルをweb.xmlかコンテキストファイルに事前に紐づける方法。

public class OfferSample {

    public String initDisplay() {
        ApplicationContext contxt = ContextLoader.getCurrentWebApplicationContext();

        // xmlのbeanIDを指定する
        OfferService service = (OfferService)contxt.getBean("offerService");

        System.out.println(service.getServiceName());

        contxt.close();
        return "offer/offer";
    }
}

ContextLoaderで呼び出せるようにするにはweb.xmlかコンテキストファイルにBeanのxmlを追記する。
・web.xmlに記載する場合

<context-param>
    <param-name>contextConfigLocation</param-name>
        <param-value>
            /WEB-INF/spring/root-context.xml
            classpath*:beans/serviceBeans.xml
        </param-value>
  </context-param>

・コンテキストファイルに記載する場合
root-context.xml(applicationContext.xml)

<import resource="classpath*:beans/serviceBeans.xml" />