質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

87.94%

Select文を実行したときに値が取れてきていない

解決済

回答 2

投稿 編集

  • 評価
  • クリップ 0
  • VIEW 6,255

score 43

t_userというテーブルがあり、このテーブルは以下の4つのカラムを持っています
user_id,user_name,user_password,user_email

また、10件のデータがあります。

このテーブルからuser_id,user_nameを取り出そうとしているのですが
Select文を実行後、結果を代入したListの中身を確認すると
10個nullが入っており、値が取れていない状況です。
※実行したsqlは後述

xmlに記載しているselect文をローカルのmysql環境で実行した場合、
結果が取れることは確認したため、sqlの構文に誤りはないと考えています。

また、結果を代入したListにnullがテーブルに存在するデータ文(10個)入っているため、
SQL自体は実行されていると考えています。

原因をご教授いただければ幸いです。

いかにソースを記載します。

メインクラス

package spring.test;

import java.io.IOException;
import java.nio.file.AccessDeniedException;
import java.nio.file.FileAlreadyExistsException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;

import org.springframework.context.ApplicationContext;
import org.springframework.context.support.FileSystemXmlApplicationContext;

public class HelloWorldTest {
    public static void main(String[] args) {



        ApplicationContext context = new FileSystemXmlApplicationContext(
                "file:/Users/nagami/Documents/workspace-sts-ver2/MyBatis/WebContent/WEB-INF/SpringTest.xml");

        SpringBean bean = (SpringBean) context.getBean("helloWorld");
        bean.show();
    }
}

メインクラスで読み込んでいるxml

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

    <bean id="helloWorld" class="spring.test.SpringBean">
    </bean>

    <context:component-scan base-package="spring.test" />

    <bean id="dataSource"
        class="org.springframework.jdbc.datasource.DriverManagerDataSource">
        <property name="driverClassName" value="com.mysql.jdbc.Driver" />
        <property name="url" value="jdbc:mysql://localhost:3306/test_app" />
        <property name="username" value="root" />
        <property name="password" value="hogehoge" />
    </bean>

    <bean id="sqlSessionFactory" class="org.mybatis.spring.SqlSessionFactoryBean">
        <property name="dataSource" ref="dataSource" />
        <property name="mapperLocations"
            value="classpath:/spring/test/sql.xml" />
    </bean>

    <bean id="sqlSession" class="org.mybatis.spring.SqlSessionTemplate">
        <constructor-arg index="0" ref="sqlSessionFactory" />
    </bean>

    <bean class="spring.test.UserDaoImpl">
        <property name="session" ref="sqlSession" />
    </bean>
</beans>

ビーンクラス

package spring.test;

import java.util.List;

import org.springframework.beans.factory.annotation.Autowired;

public class SpringBean {

    @Autowired
    private UserDao dao;

    public void show() {
     // listにnullが10個入ってきている。3行下でぬるぽで落ちる
        List<User> list = dao.getUserList();
        for (User user : list) {
            System.out.println(user.getUserId() + "-" + user.getUserName());
        }
    }
}

モデルクラス

package spring.test;

public class User {

    String userId;
    String userName;
    public String getUserId() {
        return userId;
    }
    public void setUserId(String userId) {
        this.userId = userId;
    }
    public String getUserName() {
        return userName;
    }
    public void setUserName(String userName) {
        this.userName = userName;
    }


}

インターフェース

package spring.test;

import java.util.List;

public interface UserDao {
    public List<User> getUserList();
}

sql実行クラス

package spring.test;

import java.util.List;

import org.apache.ibatis.session.SqlSession;

public class UserDaoImpl implements UserDao {

    private SqlSession session;

    public void setSession(SqlSession ss) {
        this.session = ss;
    }

    public List<User> getUserList() {
        return session.selectList("test.sql.selectUser");
    }
}

sqlを記載したxml

<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="test.sql">
    <select id="selectUser" resultType="spring.test.User">
        select user_id,user_name from t_user
    </select>
</mapper>

ローカルで同様のselect文実行時のEVD

イメージ説明

追記

package spring.test;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.apache.ibatis.session.SqlSession;

public class UserDaoImpl implements UserDao {

    private SqlSession session;

    public void setSession(SqlSession ss) {
        this.session = ss;
    }

    public List<User> getUserList() {
        // 結果取得
        List<Map<String, Object>> result = session.selectList("test.sql.selectUser");

        System.out.println("件数:" + result.size());

        result.forEach(row -> {
            row.forEach((columnName, value) -> {
                System.out.printf("columnName=%s, value=%s%n", columnName, value);
            });
        });

        return session.selectList("test.sql.selectUser");
    }
}

コンソール出力内容

イメージ説明

追記.2

イメージ説明

  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 過去に投稿した質問と同じ内容の質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

回答 2

check解決した方法

0

原因はモデルクラスにありました。
モデルクラスの変数名を取得対象のカラム名と一致させる必要がありました。

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

0

MyBatisを利用したことがあるわけではないですが、nullとなる理由はハッキリしてそうです。

ドキュメントによると

SqlSession.selectList (String statement)
Returns
List of mapped object

なので、Listが返ってきているのは分かります。
ただ、返ってきたList内容を確認してみるとおそらく分かりますが、
user_id,user_nameという名前で返ってきているだけでUserモデルの各変数と紐づけができているわけではないように思います。
一度List<Map<String, Object>>とかで受け取りループしてそれぞれにsetしてあげる必要があるのでは?

参考:MyBatis 使い方メモ#実装

10件のnull=レコードは取れているが取得したデータとの紐づけができていない
ということになりますね。
単にnewしただけのmodelって中のプロパティは初期値入れてない限りnullですので。

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2019/08/16 16:40

    row.forEach((columnName, value) -> {の部分になります。
    rowがnullの状況です。

    キャンセル

  • 2019/08/16 16:41

    なるほど。
    ちなみにデバッグ実行でブレークポイントを仕掛けて、resultの内容は確認できますか?

    キャンセル

  • 2019/08/16 16:55

    画像を追加いたしました。

    キャンセル

15分調べてもわからないことは、teratailで質問しよう!

  • ただいまの回答率 87.94%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる

関連した質問

同じタグがついた質問を見る