LoginSignup
4
1

More than 1 year has passed since last update.

xmlファイルの書き方

Last updated at Posted at 2021-08-21

XMLファイルの書き方について振り返りたい!

現在の案件先(Java)で、xmlファイルを活用する機会があり、勉強したので、ちらっと書いときます。
今回は、Javaで活用できる形式です!

的外れなことを記載していたらご指摘よろしくお願いします。

そもそもxmlファイルって?

extensible Markup Languageといい、簡単に言うと、データをやり取りするために利用されるファイルです。
HTMLと同じ、マークアップ言語であり、タグを使って、記載していきます。
(ちなみに、Javaはコンパイラ言語、PHPなどはスクリプト言語と言います)

HTMLに直接書き込んだり、DBから出力すればよくないかと思うかもしれませんが、xmlファイルに定義することでどのようなデータを出力するか明記することで、可読性や保守性を向上することができます。
特に大規模なシステムになると情報1つ出力するだけでも、細心の注意が必要なので実装することが大切です!

簡単に言うと、こんな感じです。

Okozukai.xml
<?xml version="1.0" encoding="Shift_JIS"?>
<買い物リスト>
  <内容>
    <日付>8月21日</日付>
    <買う物>カレー</買う物>
    <金額>500円</金額>
  </内容>
<内容>
    <日付>8月22日</日付>
    <買う物>ラーメン</買う物>
    <金額>600円</金額>
  </内容>
<内容>
    <日付>8月23日</日付>
    <買う物>寿司</買う物>
    <金額>15000円</金額>
  </内容>
</買い物リスト>

このような書き方をします!

詳しく見ていきましょう!

タグ一覧

まずは、必要なタグ一覧から見ていきます。

サーブレット<servlet>

要素  必須  内容 
<servlet-name> ○  web.xmlにて、サーブレットを定義するために記載する。 
<display-name> -  GUIツールによって表示される名前。 
<description> -  サーブレットのテキストによる説明。 
<servlet-class>  -  サーブレットの完全修飾名のこと。とは必ず入れる必要はありません。オプションのような感覚です。 
<jsp-file> - JSPファイルのフルパス。とは必ず入れる必要はありません。オプションのような感覚です。
<init-param> - サーブレットのキーと値の初期値を設定する。
<load-on-startup> - サーブレットがロードされる順番を設定する。値には正の整数を指定し、値が低い順から読み込まれていく。

サーブレット・マッピング

サーブレットマッピングは、サーブレット要素とURLを紐付ける役割があります。

要素  内容 
<servlet-name> web.xmlにて、サーブレットを定義するために記載する。 
<url-name> URLを解決するために用いられる。「http://host:port+WebApplicationName」 に続く部分をサーバーによって比較され、同一の場合は、サーブレットに紐づけられたサーブレットが呼び出される。

web.xmlを使用した際の流れ

web.xmlを使用した際の実際の流れを見ていく。URLによって呼び出されたサーブレットのディレクトリは以下の通りである。
URL: http://host:port/AutumnServletXml/Autumn

AutumnServletXml // コンテキストパス
 └ WEB-INF
   └ classes
     └ AutumnServlet // サーブレットパス + ここにマッピングさせるURL

 ファイルの中身はこんな感じです。

Autumn.xml
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://xmlns.jcp.org/xml/ns/javaee" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd" id="WebApp_ID" version="3.1">
  <servlet>
    <servlet-name>autumnservlet</servlet-name>
    <servlet-class>AutumnServlet</servlet-class>
  </servlet>
  <servlet-mapping>
    <servlet-name>autumnservlet</servlet-name>
    <url-pattern>/AutumnServlet</url-pattern>
  </servlet-mapping>
</web-app>

次は、サーブレットを継承したファイルです。

AutumnServlet.java

import java.io.IOException;
import java.io.PrintWriter;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class AutumnServlet extends HttpServlet {
    protected void doGet(HttpServletRequest request, HttpServletResponse response)
           throws ServletException, IOException {
        // レスポンスにコンテキストタイプの設定(何も出力するか見たいな)
        response.setContentType("text/html");

                // レスポンスで返す内容を設定
        PrintWriter out = response.getWriter();
        out.println("<html><head></head><body>");
        out.println("<p>Autumn Application</p>");
        out.println("<p>Hello Autumn!</p>");
        out.println("</body></html>");
    }
}

実行結果

クライアントからのリクエストパスはこのようになる。

http://localhost:8080/AutumnServletXml/AutumnServlet

ブラウザには、Autumn ApplicationHello Autumn!が出力されている。

解説

先程のAutumnServlet.javaの説明をしておきます!
・HttpServletを継承して、AutumnServletを作成します。
・doGetメソッドをオーバーロードして定義します。
・Context Typeにtext/htmlを指定する。
・HTMLに出力するためのoutオブジェクトを取得する。
・最後は出力する内容を定義する。
といった内容となってます!

パッケージになっている場合

パッケージとは、いくつものクラスをまとめたものです。
そこで、を見ていただくと、クラス名の完全修飾となっています。
これは、パッケージ名も含めて定義をする必要があると言うことです。
sampleというパッケージに入っているものと仮定すると、このような形式になります。

AutumnSample.xml
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://xmlns.jcp.org/xml/ns/javaee" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd" id="WebApp_ID" version="3.1">
  <servlet>
    <servlet-name>autumnservlet</servlet-name>
    <servlet-class>sample.AutumnServlet</servlet-class> // sampleが追加されてます。
  </servlet>
  <servlet-mapping>
    <servlet-name>autumnservlet</servlet-name>
    <url-pattern>/AutumnServlet</url-pattern>
  </servlet-mapping>
</web-app>

web.xmlの定義

AutumnServletXml // コンテキストパス
 └ WEB-INF
   └ classes
     └ sample // パッケージ追加
       └ Autumn // サーブレットパス + ここにマッピングさせるURL

web.xmlの<init-param>による初期設定

xmlの要素の要素を渡して、初期値設定をします。

AutumnServlet.java
<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://xmlns.jcp.org/xml/ns/javaee" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd" id="WebApp_ID" version="3.1">
  <servlet>
    <servlet-name>autumnservlet</servlet-name>
    <servlet-class>AutumnServlet</servlet-class>
    <init-param> // 追加開始
      <param-name>name</param-name>
      <param-value>John</param-value>
    </init-param>
    <init-param>
      <param-name>age</param-name>
      <param-value>89</param-value>
    </init-param> // 追加終了
  </servlet>
  <servlet-mapping>
    <servlet-name>autumnservlet</servlet-name>
    <url-pattern>/AutumnServlet</url-pattern>
  </servlet-mapping>
</web-app>

サーブレットはこのような内容です。

AutumnServlet.java

import java.io.IOException;
import java.io.PrintWriter;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class AutumnServlet extends HttpServlet {
    protected void doGet(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        // 初期設定値を取得し、変数に代入
        String name = getInitParameter("name");
        String age = getInitParameter("age");

        response.setContentType("text/html");

        PrintWriter out = response.getWriter();
        out.println("<html><head></head><body>");
        out.println("<p>Simple Application</p>");
        out.println("<p>Hello Autumn! + " "  + "名前は" + name + " " + age + ""</p>");
        out.println("</body></html>");
    }
}

実行結果

ルートパスは、変わりません。
出力内容としては、Simple ApplicationHello Autumn! 名前はjohn 89歳と出力されます。

解説

大きくは変わっていませんが、が使用されています。
getInitParameter("name")、getInitParameter("age")でそれぞれ値をxmlファイルから呼び出しています。

デフォルトサーブレット

指定されたサーブレットパスがなくても、デフォルトで用意しておいたHTMLを出力します。

ディレクトリは以下の通りです。

AutumnServletXml // コンテキストパス
 └ WEB-INF
   └ classes
     └ AutumnServlet // サーブレットパス + ここにマッピングさせるURL
     └ Default // デフォルト追加

web.xmlファイルの内容を定義します。

web.xml

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://xmlns.jcp.org/xml/ns/javaee" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd" id="WebApp_ID" version="3.1">
  <servlet>
    <servlet-name>autumnservlet</servlet-name>
    <servlet-class>AutumnServlet</servlet-class>
  </servlet>
  <servlet>
    <servlet-name>defaultservlet</servlet-name>
    <servlet-class>DefaultServlet</servlet-class>
  </servlet>
  <servlet-mapping>
    <servlet-name>autumnservlet</servlet-name>
    <url-pattern>/AutumnServlet</url-pattern>
  </servlet-mapping>
  <servlet-mapping>
    <servlet-name>defaultservlet</servlet-name>
    <url-pattern>/</url-pattern>
  </servlet-mapping>
</web-app>

サーブレットは以下の内容です。

DefaultServlet.java

import java.io.IOException;
import java.io.PrintWriter;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

public class DefaultServlet extends HttpServlet {
    protected void doGet(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {

        response.setContentType("text/html");

        PrintWriter out = response.getWriter();
        out.println("<html><head></head><body>");
        out.println("<p>Servlet not found.</p>");
        out.println("<p>Default Servlet</p>");
        out.println("</body></html>");
    }
}

実行結果

以下のような存在しないパスを指定した際に、デフォルトのHTMLが返されます。

// 存在しないパス
http://localhost:8080/AutumnServletXml/SummerServlet

出力内容は、Servlet not found.,Default Servletとなる。

解説

サーブレットの内容としては変わらないが、web.xmlのパス指定の際に"/"を定義してあげたことで、存在しないパスを指定した時でも、HTMLが表示されるようになった。

おまけ

web.xml
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://xmlns.jcp.org/xml/ns/javaee" xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd" id="WebApp_ID" version="3.1">

この1行が何をしているのかの解説もしておきます!

xmlns:xsi, xmlns, xmlns:schemaLocation

これは、名前空間を定義してあげています。名前空間とはxmlに限った話ではなく、ざまざまな場面で使われています。

必要性としては、HTMLには複数のxmlファイルが利用されることがあるからです。万が一、どのxmlファイルにもtitleタグがあった場合、どちらを参照したら良いか困惑してしまいます。そこで、「1号室」などを指定してあげれば、読み込む側も、困惑することなく利用することができるといった内容です。

ただ、「1号室」という定義あったとしても、星のリゾートの「1号室」なのか、帝国ホテルの「1号室」なのか分からないですよね。
したがって、どのホテルの「1号室」なのかを定義してあげることで、識別できるようにしてあげます!

イメージとしては、ルート要素(ホテルの種類)を定義する。次に、ルート要素にURL(何号室)を定義するといった順番です。

まずは、ルート要素を定義してあげます。ルート要素は、xmlns要素で定義します。

web.xml
xmlns="http://xmlns.jcp.org/xml/ns/javaee" 

次に、URLを定義してあげます。

web.xml
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 

最後に、schemaLocationですが、これは、ファイルの場所を指定してあげます。というのも、名前空間はあくまで識別するためのものであり、スキーマの場所を示しているわけではないからです。

web.xml
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd"

このタグにより、どうファイル内の同じ識別します!

id, version

idに関しては、どのアプリのIDなのか(必須ではない)、versionは、どのバージョンのサーブレットを使用しているかなどを定義します(javaでサーブレットを使用する場合で、他の場合は別のバージョンを指定する)。

参照したサイト

https://ponsuke-tarou.hatenablog.com/entry/2021/06/07/224803
https://www.mlab.im.dendai.ac.jp/~yamada/web/xml/namespace.html
https://www.mlab.im.dendai.ac.jp/~yamada/web/xml/namespace.html

4
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
4
1