intra-mart Accel Platform / TERASOLUNA Global Framework プログラミングガイド

第5版 2014-09-01

«  ショートカットアクセス機能   ::   コンテンツ

参考( TERASOLUNA Global Framework on Accel Platform アーキテクチャ )

TERASOLUNA Global Framework (http://terasoluna.org/) は、Spring Framework (http://projects.spring.io/spring-framework/) をベースに構成されるJavaフレームワークです。
TERASOLUNA Global Framework の詳細については TERASOLUNA Global Framework Development Guideline にて公開されています。
本項では、 intra-mart Accel Platform と TERASOLUNA Global Framework によるフルスタックフレームワークについて説明します。

TERASOLUNA Global Framework on Accel Platform の構成

intra-mart Accel Platform 上に TERASOLUNA Global Framework を組み込んだ「フルスタックフレームワーク」のイメージは下図の通りです。
../../_images/tgfw_stack_on_iap.png
TERASOLUNA Global Framework は、下記の通り、Spring Framework がベースで構成され、トランザクショントークンチェック、コードリスト、例外ハンドリングやロギング等の機能を提供し、その活用方法を「 TERASOLUNA Global Framework Development Guideline 」として提供しています。
アプリケーション層 Spring MVC / Bean Validation
ドメイン層 Spring Framework
インフラストラクチャ層 Spring Data JPA (Hibernate) / MyBatis
TERASOLUNA Global Framework on Accel Platform では、intra-mart Accel Platform が提供する以下の機能を利用して、TERASOLUNA Global Framework のアプリケーションを効率よく開発することができます。

コラム

intra-mart Accel Platform が提供する各機能の使い方については上記リンクより参照にしてください。

TERASOLUNA Global Framework との対応

TERASOLUNA Global Framework Development Guideline で想定している TERASOLUNA Global Framework のアーキテクチャの TERASOLUNA Global Framework on Accel Platform 上での対応は以下の通りです。

機能 対応 備考
データアクセス(共通編) image_ok シンプルなCRUD操作で動作確認を行っております。
データアクセス(JPA編) image_ok シンプルなCRUD操作で動作確認を行っております。
データアクセス(Mybatis2編) image_ok シンプルなCRUD操作で動作確認を行っております。
排他制御 image_ok  
入力チェック image_ok  
ロギング image_notice Logger, MDCは intra-mart Accel Platform のものを使用してください。 また、 ログ を参照してください。 TraceLoggingInterceptor, ExceptionLoggerについては、 TERASOLUNA Global Framework Development Guideline を参照してください。
例外ハンドリング image_ok  
セッション管理 image_notice Spring Securityを使うものについては対象外です。
メッセージ管理 image_ng IntramartMessageSource を使用してください。 また、 多言語化されたメッセージを取得する を参照してください。
プロパティ管理 image_ok  
ページネーション image_ng imuiTableを使用してください。
二重送信防止 image_ok  
国際化 image_notice IntramartMessageSource, AccountLocaleResolverを使用してください。 また、 国際化 を参照してください。
コードリスト image_ok Bean定義 applicationContext-im_tgfw_web.xml にコードリストの設定を記述しています。 <mvc:mapping>のpath属性は、適用対象のパスを設定してください。
Ajax image_ok  
ファイルアップロード image_notice Servlet 3.0の機能は非対応です。 multipartResolverにはCommonsMultipartResolverを設定しています。 また、 Storage を参照してください。
ファイルダウンロード image_ok Storage を参照してください。
Tiles image_ng intra-mart Accel Platform のテーマ機能を使用してください。
システム時刻 image_notice org.terasoluna.gfw.common.date.JdbcAdjustedDateFactory を使用する場合、 dataSourceプロパティにはシェアードデータソースを指定してください。 シェアードデータソースの設定は、 DataSourceSpring Data JPAを使用したプログラミング方法MyBatisを使用したプログラミング方法 を参照してください。
ユーティリティ(dozer) image_ok  
ユーティリティ(joda time) image_ok joda-timeのjarは %RESIN_HOME%/lib に配置してください。

TERASOLUNA Global Framework Development Guideline に記載されている TERASOLUNA Global Framework のセキュリティ対策についての TERASOLUNA Global Framework on Accel Platform 上での対応は以下の通りです。

セキュリティ対策 対応 備考
Spring Security (認証、パスワードハッシュ化、認可) image_ng 認証、パスワードハッシュ化、認可機能については、 intra-mart Accel Platform の認証、認可を使用してください。 intra-mart Accel Platform でもパスワードのハッシュ化を行っています。
XSS対策 image_ok  
CSRF対策 image_ng intra-mart Accel Platform のimSecureToken タグを使用してください。

TERASOLUNA Global Framework on Accel Platform におけるBean定義の既定値

Spring MVC では、DispatcherServlet というサーブレットクラスが提供されています。
DispatcherServletは、クライアントからの要求に対して、要求情報からコントローラを探し、コントローラを呼び出す役割を担います。
intra-mart Accel Platform では、クライアントからの要求に対して、該当するプログラムを探し、認可のチェックをし、見つかったプログラムを呼び出す「ルーティング機構」があります。
intra-mart Accel Platform では、この「ルーティング機構」からSpring MVCのコントローラを呼び出す機構が組み込まれています。

コラム

「ルーティング機構」の仕組みについては、「認可」ページを参考にしてください。
Spring MVCでは通常、1つのWebアプリケーションに複数のDispatcherServletを登録し、サーブレットごとにBean定義を行うことができますが、
intra-mart Accel Platform では、DispatcherServletを拡張したサーブレットクラスが1つだけ登録されており、このサーブレットクラスを複数登録することはできません。
そのため、intra-mart Accel Platform ではすべてのBean定義はWebアプリケーション上で共有されることになります。
intra-mart Accel Platform では、あらかじめ下記ファイルにてBean定義が行われています。
  • <Jugglingプロジェクト>/classes/META-INF/spring/applicationContext-im_tgfw_common.xml
  • <Jugglingプロジェクト>/classes/META-INF/spring/applicationContext-im_tgfw_web.xml
  • <Jugglingプロジェクト>/classes/META-INF/spring/SpringMVCServlet-servlet.xml
  • <Jugglingプロジェクト>/classes/META-INF/spring/applicationContext-jpa.xml
  • <Jugglingプロジェクト>/classes/META-INF/spring/applicationContext-mybatis.xml
これらのBean定義は、intra-mart Accel Platform のテナント上で共有されるため、セットアップガイドに記載のない内容以外は基本変更しないようにしてください。
以下、intra-mart Accel Platform へのSpring MVCの組込み内容と上記Bean定義ファイルの初期値について示します。

web.xml

<web-app xmlns="http://java.sun.com/xml/ns/javaee"
         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         metadata-complete="false"
         version="3.0"
         xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd">

  : (省略)

  <!-- Web アプリケーション起動時に、クラスパス上の/META-INF/spring/内のapplicationContextで始まるBean定義ファイルをロード させる設定-->
  <context-param>
    <param-name>contextConfigLocation</param-name>
    <param-value>classpath*:/META-INF/spring/applicationContext*.xml</param-value>
  </context-param>
  <listener>
    <listener-class>jp.co.intra_mart.framework.extension.spring.web.servlet.SpringServletContextListener</listener-class>
  </listener>

  : (省略)

  <!-- 「ルーティング機構」用にDispatcherServletを拡張したサーブレットを登録 -->
  <servlet>
    <servlet-name>SpringMVCServlet</servlet-name>
    <servlet-class>jp.co.intra_mart.framework.extension.spring.web.servlet.IntramartDispatcherServlet</servlet-class>
    <init-param>
      <param-name>contextConfigLocation</param-name>
      <param-value>classpath:/META-INF/spring/SpringMVCServlet-servlet.xml</param-value>
    </init-param>
    <load-on-startup>1</load-on-startup>
    <multipart-config/>
  </servlet>

  : (省略)

</web-app>

applicationContext-im_tgfw_common.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"
    xmlns:context="http://www.springframework.org/schema/context"
    xmlns:tx="http://www.springframework.org/schema/tx"
    xsi:schemaLocation="http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd
        http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd">

    <!-- a bean which holds the root application context -->
    <bean class="jp.co.intra_mart.system.extension.spring.context.ApplicationContextHolder" />

    <!-- message source which loads from 'WEB-INF/conf/message/**/*.properties' -->
    <bean id="messageSource" class="jp.co.intra_mart.framework.extension.spring.message.IntramartMessageSource" />

    <!-- bean validation (JSR-303) -->
    <bean id="validator" class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean">
        <property name="validationMessageSource" ref="messageSource" />
    </bean>

    <!-- transaction manager (JTA) -->
    <bean id="transactionManager" class="org.springframework.transaction.jta.JtaTransactionManager" />

    <!-- enable the configuration of transactional behavior based on annotations -->
    <tx:annotation-driven transaction-manager="transactionManager"/>

    <!-- intra-mart tenant datasource -->
    <bean id="dataSource" class="jp.co.intra_mart.framework.extension.spring.datasource.TenantDataSource" />

    <!-- intra-mart shared datasource -->
    <!--
         [Note] If you use the shared datasource, please uncomment/enable the following setting
                and set the bean's id and the connectId's value.
    -->
    <!-- 
    <bean id="sharedDataSource" class="jp.co.intra_mart.framework.extension.spring.datasource.SharedDataSource">
        <constructor-arg name="connectId" value="xxxxxxxxxxxxxx" />
    </bean>
     -->

    <!-- property placeholder setting -->
    <context:property-placeholder location="classpath*:/META-INF/spring/*.properties" />

    <!-- dozer setting -->
    <bean class="org.dozer.spring.DozerBeanMapperFactoryBean">
        <property name="mappingFiles" value="classpath*:/META-INF/dozer/**/*-mapping.xml" />
    </bean>

    <!-- Exception Code Resolver. -->
    <bean id="exceptionCodeResolver"
        class="org.terasoluna.gfw.common.exception.SimpleMappingExceptionCodeResolver">
        <!-- Setting and Customization by project. -->
        <property name="exceptionMappings">
            <map>
                <entry key="ResourceNotFoundException" value="w.im.fw.0001" />
                <entry key="BusinessException" value="w.im.fw.0002" />
                <entry key="InvalidTransactionTokenException" value="w.im.fw.0004" />
            </map>
        </property>
        <property name="defaultExceptionCode" value="e.im.fw.0001" />
    </bean>

    <!-- Exception Logger. -->
    <bean id="exceptionLogger"
        class="org.terasoluna.gfw.common.exception.ExceptionLogger">
        <property name="exceptionCodeResolver" ref="exceptionCodeResolver" />
    </bean>

</beans>

applicationContext-im_tgfw_web.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"
    xmlns:mvc="http://www.springframework.org/schema/mvc" xmlns:util="http://www.springframework.org/schema/util"
    xmlns:context="http://www.springframework.org/schema/context" xmlns:aop="http://www.springframework.org/schema/aop"
    xsi:schemaLocation="http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd
        http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd
        http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util.xsd
        http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd">

    <!-- locale resolver -->
    <bean id="localeResolver" class="jp.co.intra_mart.framework.extension.spring.web.servlet.i18n.AccountLocaleResolver" />

    <!-- SpringMVCRoute needs HandlerSelector bean. -->
    <bean id="handlerSelector" class="jp.co.intra_mart.system.router.spring.HandlerSelector" init-method="init" />

    <!-- view components -->
    <context:component-scan base-package="jp.co.intra_mart.framework.extension.spring.web.servlet.view" />

    <bean class="org.springframework.web.servlet.view.BeanNameViewResolver">
        <property name="order" value="0" />
    </bean>
    <!-- prefix for InternalResourceViewResolver -->
    <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
        <property name="prefix" value="/WEB-INF/views/" />
        <property name="order" value="1" />
    </bean>

    <!-- multipart resolver -->
    <bean id="multipartResolver" class="org.springframework.web.multipart.commons.CommonsMultipartResolver" />

    <!-- support for annotation-driven MVC controllers -->
    <mvc:annotation-driven conversion-service="conversionService">
        <!-- transaction token -->
        <mvc:argument-resolvers>
            <bean class="org.terasoluna.gfw.web.token.transaction.TransactionTokenContextHandlerMethodArgumentResolver" />
        </mvc:argument-resolvers>
        <!-- jackson message converter -->
        <mvc:message-converters register-defaults="true">
            <bean class="org.springframework.http.converter.json.MappingJacksonHttpMessageConverter">
                <property name="objectMapper">
                    <bean class="jp.co.intra_mart.framework.extension.spring.http.converter.json.AccountDateObjectMapper" />
                </property>
            </bean>
        </mvc:message-converters>
    </mvc:annotation-driven>

    <bean id="conversionService"
          class="org.springframework.format.support.FormattingConversionServiceFactoryBean">
        <property name="formatters">
            <set>
                <bean class="jp.co.intra_mart.framework.extension.spring.format.datetime.AccountDateFormatAnnotationFormatterFactory"/>
                <bean class="jp.co.intra_mart.framework.extension.spring.format.datetime.AccountDateTimeFormatAnnotationFormatterFactory"/>
                <bean class="jp.co.intra_mart.framework.extension.spring.format.datetime.AccountTimeFormatAnnotationFormatterFactory"/>
            </set>
        </property>
    </bean>


    <!-- MVC interceptors -->
    <mvc:interceptors>
        <!-- transaction token -->
        <mvc:interceptor>
            <mvc:mapping path="/**" /> <!-- configure the path to specify the package of controllers. -->
            <bean class="org.terasoluna.gfw.web.token.transaction.TransactionTokenInterceptor">
                <constructor-arg value="10" />
            </bean>
        </mvc:interceptor>
        <!-- code list -->
        <mvc:interceptor>
            <mvc:mapping path="/**" /> <!-- configure the path to specify the package of controllers. -->
            <bean class="org.terasoluna.gfw.web.codelist.CodeListInterceptor">
                <property name="codeListIdPattern" value="CL_.+" />
            </bean>
        </mvc:interceptor>
        <!--
           [Note] If you use the JPA, please uncomment/enable the following setting.
                  Please see the following link for more detail.
                  > http://static.springsource.org/spring/docs/3.2.x/javadoc-api/org/springframework/orm/jpa/support/OpenEntityManagerInViewInterceptor.html
           [Note] configure the path to specify the package of controllers.
        -->
        <!-- 
        <mvc:interceptor>
            <mvc:mapping path="/**" />
            <bean class="org.springframework.orm.jpa.support.OpenEntityManagerInViewInterceptor" />
        </mvc:interceptor>
        -->
    </mvc:interceptors>

    <!-- transaction token -->
    <bean name="requestDataValueProcessor" class="org.terasoluna.gfw.web.mvc.support.CompositeRequestDataValueProcessor">
        <constructor-arg>
            <util:list>
                <bean class="org.terasoluna.gfw.web.token.transaction.TransactionTokenRequestDataValueProcessor" />
            </util:list>
        </constructor-arg>
    </bean>

    <!-- Setting Exception Handling. -->
    <!-- Exception Resolver. -->
    <bean class="org.terasoluna.gfw.web.exception.SystemExceptionResolver">
        <property name="exceptionCodeResolver" ref="exceptionCodeResolver" />
        <!-- Setting and Customization by project. -->
        <property name="order" value="3" />
        <property name="exceptionMappings">
            <map>
                <entry key="ResourceNotFoundException" value="im_tgfw/common/error/resourceNotFoundError.jsp" />
                <entry key="BusinessException" value="im_tgfw/common/error/businessError.jsp" />
                <entry key="InvalidTransactionTokenException" value="im_tgfw/common/error/transactionTokenError.jsp" />
            </map>
        </property>
        <property name="statusCodes">
            <map>
                <entry key="im_tgfw/common/error/resourceNotFoundError" value="404" />
                <entry key="im_tgfw/common/error/businessError" value="200" />
                <entry key="im_tgfw/common/error/transactionTokenError" value="409" />
            </map>
        </property>
        <property name="defaultErrorView" value="im_tgfw/common/error/systemError.jsp" />
        <property name="defaultStatusCode" value="500" />
    </bean>
    <!-- AOP. -->
    <bean id="handlerExceptionResolverLoggingInterceptor"
        class="org.terasoluna.gfw.web.exception.HandlerExceptionResolverLoggingInterceptor">
        <property name="exceptionLogger" ref="exceptionLogger" />
    </bean>
    <aop:config>
        <aop:advisor advice-ref="handlerExceptionResolverLoggingInterceptor"
            pointcut="execution(* org.springframework.web.servlet.HandlerExceptionResolver.resolveException(..))" />
    </aop:config>

</beans>

SpringMVCServlet-servlet.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"
    xmlns:context="http://www.springframework.org/schema/context"
    xmlns:mvc="http://www.springframework.org/schema/mvc"
    xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd
        http://www.springframework.org/schema/mvc http://www.springframework.org/schema/mvc/spring-mvc.xsd">

</beans>

applicationContext-jpa.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"
    xmlns:util="http://www.springframework.org/schema/util"
    xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
        http://www.springframework.org/schema/util http://www.springframework.org/schema/util/spring-util.xsd"
    >

    <bean id="jpaVendorAdapter"
        class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">
        <property name="showSql" value="false" />
        <property name="database">
            <value>POSTGRESQL</value>
            <!-- 
            <value>DB2</value>
            <value>DEFAULT</value>
            <value>HSQL</value>
            <value>INFORMIX</value>
            <value>MYSQL</value>
            <value>ORACLE</value>
            <value>POSTGRESQL</value>
            <value>SQL_SERVER</value>
            <value>SYBASE</value>
             -->
        </property>
    </bean>
    <util:map id="hibernateProperties">
        <entry key="hibernate.hbm2ddl.auto" value="none" />
        <entry key="hibernate.ejb.naming_strategy"
               value="org.hibernate.cfg.ImprovedNamingStrategy" />
        <entry key="hibernate.connection.charSet" value="UTF-8" />
        <entry key="hibernate.show_sql" value="false" />
        <entry key="hibernate.format_sql" value="false" />
        <entry key="hibernate.use_sql_comments" value="true" />
        <entry key="hibernate.jdbc.batch_size" value="30" />
        <entry key="hibernate.jdbc.fetch_size" value="100" />
        <entry key="hibernate.temp.use_jdbc_metadata_defaults" value="false" />
        <entry key="hibernate.transaction.jta.platform">
            <value>org.hibernate.service.jta.platform.internal.ResinJtaPlatform</value>
            <!-- 
            <value>org.hibernate.service.jta.platform.internal.ResinJtaPlatform</value>
            <value>org.hibernate.service.jta.platform.internal.WeblogicJtaPlatform</value>
            <value>org.hibernate.service.jta.platform.internal.WebSphereExtendedJtaPlatform</value>
             -->
        </entry>
    </util:map>

    <bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
        <property name="packagesToScan" value="jp.co.intra_mart.framework.extension.spring.entity" />
        <property name="jtaDataSource" ref="dataSource" />
        <property name="jpaVendorAdapter" ref="jpaVendorAdapter" />
        <property name="jpaPropertyMap" ref="hibernateProperties" />
        <property name="persistenceUnitName" value="tenant" />
    </bean>

<!-- 
	
    <bean id="sharedEntityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
        <property name="packagesToScan" value="jp.co.intra_mart.framework.extension.spring.entity" />
        <property name="jtaDataSource" ref="sharedDataSource" />
        <property name="jpaVendorAdapter" ref="jpaVendorAdapter" />
        <property name="jpaPropertyMap" ref="hibernateProperties" />
        <property name="persistenceUnitName" value="shared" />
    </bean>
-->
</beans>

applicationContext-mybatis.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 id="sqlMapClient" class="org.springframework.orm.ibatis.SqlMapClientFactoryBean" scope="singleton">
        <property name="configLocations" value="classpath*:/META-INF/mybatis/config/*sqlMapConfig.xml" />
        <property name="mappingLocations" value="classpath*:/META-INF/mybatis/sql/**/*-sqlmap.xml" />
        <property name="dataSource" ref="dataSource" />
    </bean>

    <bean id="queryDAO"
        class="jp.terasoluna.fw.dao.ibatis.QueryDAOiBatisImpl">
        <property name="sqlMapClient" ref="sqlMapClient" />
    </bean>

    <bean id="updateDAO"
        class="jp.terasoluna.fw.dao.ibatis.UpdateDAOiBatisImpl">
        <property name="sqlMapClient" ref="sqlMapClient" />
    </bean>

    <bean id="spDAO"
        class="jp.terasoluna.fw.dao.ibatis.StoredProcedureDAOiBatisImpl">
        <property name="sqlMapClient" ref="sqlMapClient" />
    </bean>

    <bean id="queryRowHandleDAO"
        class="jp.terasoluna.fw.dao.ibatis.QueryRowHandleDAOiBatisImpl">
        <property name="sqlMapClient" ref="sqlMapClient" />
    </bean>
    
<!-- 

    <bean id="sharedSqlMapClient" class="org.springframework.orm.ibatis.SqlMapClientFactoryBean" scope="singleton">
        <property name="configLocations" value="classpath*:/META-INF/mybatis/config/*sqlMapConfig.xml" />
        <property name="mappingLocations" value="classpath*:/META-INF/mybatis/sql/**/*-sqlmap.xml" />
        <property name="dataSource" ref="sharedDataSource" />
    </bean>

    <bean id="sharedQueryDAO"
        class="jp.terasoluna.fw.dao.ibatis.QueryDAOiBatisImpl">
        <property name="sqlMapClient" ref="sharedSqlMapClient" />
    </bean>

    <bean id="sharedUpdateDAO"
        class="jp.terasoluna.fw.dao.ibatis.UpdateDAOiBatisImpl">
        <property name="sqlMapClient" ref="sharedSqlMapClient" />
    </bean>

    <bean id="sharedSpDAO"
        class="jp.terasoluna.fw.dao.ibatis.StoredProcedureDAOiBatisImpl">
        <property name="sqlMapClient" ref="sharedSqlMapClient" />
    </bean>

    <bean id="sharedQueryRowHandleDAO"
        class="jp.terasoluna.fw.dao.ibatis.QueryRowHandleDAOiBatisImpl">
        <property name="sqlMapClient" ref="sharedSqlMapClient" />
    </bean>
 -->
</beans>

«  ショートカットアクセス機能   ::   コンテンツ