Spring MVC行列変数のクイックガイド

Spring MVCマトリックス変数のクイックガイド

1. 概要

URI仕様RFC 3986は、URIパスパラメーターを名前と値のペアとして定義しました。 マトリックス変数は、Springの造語であり、URIパスパラメーターを渡したり解析したりするための代替実装です。

行列変数のサポートはSpringMVC 3.2で利用可能になり、simplify requests with a large number of parametersを対象としています。

この記事では、URIの異なるパスセグメント内で変数またはオプションのパスパラメーターを使用する複雑なGETリクエストを単純化する方法を示します。

2. 設定

Spring MVCマトリックス変数を有効にするには、構成から始めましょう。

@Configuration
public class WebConfig implements WebMvcConfigurer {

    @Override
    public void configurePathMatch(PathMatchConfigurer configurer) {
        UrlPathHelper urlPathHelper = new UrlPathHelper();
        urlPathHelper.setRemoveSemicolonContent(false);
        configurer.setUrlPathHelper(urlPathHelper);
    }
}

それ以外の場合は、デフォルトで無効になっています。

3. 行列変数の使用方法

これらの変数は、パスの任意の部分に表示でき、等号(「=」)を使用して値を指定し、セミコロン(「;」)を使用して各マトリックス変数を区切ります。 同じパスで、同じ変数名を繰り返すか、文字のコンマ( ’、’)を使用して異なる値を区切ることもできます。

この例には、従業員に関する情報を提供するコントローラーがあります。 各従業員には作業領域があり、その属性で検索できます。 検索には次のリクエストを使用できます。

http://localhost:8080/spring-mvc-java/employeeArea/workingArea=rh,informatics,admin

またはこのように:

http://localhost:8080/spring-mvc-java
  /employeeArea/workingArea=rh;workingArea=informatics;workingArea=admin

Spring MVCでこれらの変数を参照する場合は、アノテーション@MatrixVariableを使用する必要があります。

この例では、Employeeクラスを使用します。

public class Employee {

    private long id;
    private String name;
    private String contactNumber;

    // standard setters and getters
}

また、Companyクラス:

public class Company {

    private long id;
    private String name;

    // standard setters and getters
}

これらの2つのクラスは、リクエストパラメータをバインドします。

4. 行列変数のプロパティの定義

変数に必須またはデフォルトのプロパティを指定できます。 次の例では、contactNumberが必要であるため、次のようにパスに含める必要があります。

http://localhost:8080/spring-mvc-java/employeesContacts/contactNumber=223334411

リクエストは次の方法で処理されます。

@RequestMapping(value = "/employeesContacts/{contactNumber}",
  method = RequestMethod.GET)
@ResponseBody
public ResponseEntity> getEmployeeBycontactNumber(
  @MatrixVariable(required = true) String contactNumber) {
    List employeesList = new ArrayList();
    ...
    return new ResponseEntity>(employeesList, HttpStatus.OK);
}

その結果、連絡先番号223334411を持つすべての従業員を取得します。

5. 補数パラメータ

行列変数はパス変数を補完できます。

たとえば、従業員の名前を検索していますが、連絡先番号の開始番号を含めることもできます。

この検索のリクエストは次のようになります。

http://localhost:8080/spring-mvc-java/employees/John;beginContactNumber=22001

リクエストは次の方法で処理されます。

@RequestMapping(value = "/employees/{name}", method = RequestMethod.GET)
@ResponseBody
public ResponseEntity> getEmployeeByNameAndBeginContactNumber(
  @PathVariable String name, @MatrixVariable String beginContactNumber) {
    List employeesList = new ArrayList();
    ...
    return new ResponseEntity<>(employeesList, HttpStatus.OK);
}

その結果、連絡先番号が22001であるか、名前がJohnであるすべての従業員が取得されます。

6. すべての行列変数のバインド

何らかの理由で、パスで使用可能なすべての変数を取得したい場合は、それらをMapにバインドできます。

http://localhost:8080/spring-mvc-java/employeeData/id=1;name=John;contactNumber=2200112334

このリクエストは、次の方法で処理されます。

@GetMapping("employeeData/{employee}")
@ResponseBody
public ResponseEntity> getEmployeeData(
  @MatrixVariable Map matrixVars) {
    return new ResponseEntity<>(matrixVars, HttpStatus.OK);
}

もちろん、パスの特定の部分の行列変数へのバインドを制限できます。 たとえば、次のようなリクエストがある場合:

http://localhost:8080/spring-mvc-java/
  companyEmployee/id=2;name=Xpto/employeeData/id=1;name=John;
  contactNumber=2200112334

そして、employeeDataに属するすべての変数のみを取得したいと思います。次に、入力パラメータとして次を使用する必要があります。

@RequestMapping(
 value = "/companyEmployee/{company}/employeeData/{employee}",
 method = RequestMethod.GET)
@ResponseBody
public ResponseEntity> getEmployeeDataFromCompany(
  @MatrixVariable(pathVar = "employee") Map matrixVars) {
  ...
}

7. 部分的なバインディング

単純さは別として、柔軟性は別の利点であり、マトリックス変数はさまざまな方法で使用できます。 たとえば、各パスセグメントから各変数を取得できます。 次のリクエストを検討してください。

http://localhost:8080/spring-mvc-java/
  companyData/id=2;name=Xpto/employeeData/id=1;name=John;
  contactNumber=2200112334

companyDataセグメントの行列変数nameのみを知りたい場合は、入力パラメーターとして次を使用する必要があります。

@MatrixVariable(value="name", pathVar="company") String name

8. 結論

この記事では、マトリックス変数を使用できるさまざまな方法のいくつかを説明しました。

この新しいツールが複雑すぎるリクエストをどのように処理できるかを理解すること、または検索を区切るためにパラメータを追加するのに役立つことを理解することが重要です。

これらすべての例とコードスニペットの実装は、GitHub projectにあります。これはMavenベースのプロジェクトであるため、そのままインポートして実行するのは簡単です。