Q135:日付の表示
Q135-1:
問題は1行6列のテーブルがあり、文字列と日付列があります。このテーブルにMySQLから読み込んだ(SQL:select xx from yyyy)データを一つずつ設定していますが、「型が異なる 値が含まれています。」のエラーが発生するため、読み込んだ日付列を一度日付入力フィールドに「日付を設定する」で設定、これをテーブルの日付列へ「セルの値を設定する」で行うと、データがNullとなり設定できなくなります。
日付入力フィールドには確かに日付が2011-07-30の形で保存されたのはデバッガーで確認していますが、そのデータがテーブルに設定できないという問題です。このテーブルは他のデータソースからもデータを設定していますが、(ある欄に選択オプションを設定、選択すると違うデータソースからデータをロード)こちらは問題なく機能します。 問題の列を文字列に設定すれば、データは2011-07-30の形でロードできますが、他のテーブルからのデータは余分な時間部分も00-00-00の形でロードされるので、これは問題となります。
本来は日付表示 2011-07-31を他の表示と合わせて2011/07/30に変更したいのですが、現状は文字列でロードできても2011-07-30の形でしかロードできません。
列を日付にしてあるときは、列の形式をyyyy/MM/ddで設定しました。
MySQLへデータを一括ロードした時には、2011/07/30の形式で保存していますが読み出すと2011-07-30の形となり、これはMySQLの保存形式によるものかと考えています。MySQLのデータ形式設定では日付(Date)で設定してあります。尚、他のデータソースのデータはMySQLに保存してあるデータですが、こちらは2011/07/30 00:00:00の形で表示できています。
サンプルも参照しましたが、ヒントはなく、困っている次第です。カレンダーコンポーネントを使っても試行しましたが、引数の設定が理解できず、うまくいっていません。
A135-1:
1)[データベースアクセス]コンポーネントでSQL文を実行し、取得した結果はテーブル型データとなります。
MySQL内でDate, DateTime等日付型のデータは、[データベースアクセス]で取得すると、MZPlatform上では日付型のデータとなります。
@MySQL内のテーブルの列型が文字列型になっていないか、今一度ご確認下さい。
2)「型が異なる値が含まれています」というエラーメッセージは、データとして受け付けられない形式のデータを列に追加や設定しようとした時に起こります。
数値型のセルに「ABC」という文字列を設定しようとした場合にも起こります。
[テーブル]の日付型の列には「2011-8-12」という『文字列』は設定できません。また、NULL値は設定できますが、「空白文字列」は設定できません。
[日付入力フィールド]にはデフォルトの表示形式のままでは、「2011-8-12」という『文字列』は設定できません。「日付を設定する(Object)」で設定されたように見えるのですが、値として確定されていません。NULLのままか、何か一度先に確定された値が維持されています。
「日付を設定する(Object)」では、日付型のデータを引数に設定するのが望ましいかと思います。日付型のデータは文字列として見ると「Fri Aug 1212:00:59 JST 2011」といった形式に見えるものです。文字列を引数とする場合には「文字列を設定した後、その文字列で値を確定する(String)」をお勧めします。
A「日付を設定する(Object)」の引数は文字列になってはいないでしょうか。
もし引数に「Select結果テーブルから「指定セルの値を取得」」とした結果を入れているとしたら、やはりSelect結果テーブルの問題の列は、この時点で既に文字列型となっている可能性が高いです。
以上、元々のデータベース、あるいはデータベースから取得直後に既に文字列型になってしまっているのではないかと推測しております。
@、Aをまずはご確認下さい。
もちろんこちらで把握していない事由も考えられますので、何かお気付きの点がございましたら、どうぞお知らせ下さい。
根本的な型の相違の理由が見つかれば一番よいですが、それまでの回避方法として、[日付入力フィールド]の表示モードを、「その他」>「yyyy-MM-dd」としてお試し下さい。「日付を設定する(Object)」で「2011-8-12」が値として受け付けられるようになります。
Q135-2:
日付入力フィールドを使い、2011-08-01の形で設定し、このデータを問題の表示テーブルのカラムに設定すると、カラムが文字列型では、表示は2011-08-01で行えますが、日付型では「型が異なる値が含まれています」というエラーになります。
このカラムは他のテーブルからの日付データも表示させているので、文字列型にすると2011-08-01 00-00-00と不要な時間まで表示されます。
MySQL データベースでのフィールドの設定は日付型になっているのに、読み出すと文字列型になっている症状から、再度検討しました。
いろいろと試しているうちに、問題のデータはエクセルファイルから日付型データを読み込んでいますが、書き込むときに文字列型でMySQLに書き込まれているようだと判断して、MZ プラットフォームのFAQを検索したところ、エクセルファイルのデータは文字列型で保存される、データ型を日付型に変更する項目(FAQ19)が見つかり、テーブルを読み込んだ後、該当カラムを日付型に変更するステップをいれたところ、日付型で保存されるようになりました。
テーブルを一度テーブル格納変数へ読み込ませていましたので、テーブル格納変数でカラムのデータ型を変更しましたが、この方法では機能せず、もともとのテーブル自体に変更を加えたところ、うまくいきました。
上記方法で文字列型を日付型に変更して懸案の問題は解決しましたが、ひとつ余波がありました。日付のカラムが決まっていない場合、データとして0000/00/00を挿入していましたが、日付型にすると0002/11/30と変な日付に変換されてしまいます。MySQLの問題のような気がしますが、何かヒントがあればご教授いただけませんか?エクセルから読み込んだ0000/00/00も同様に返還されます。よろしくお願いいたします。
A135-2:
1)
>日付のカラムが決まっていない場合、データとして0000/00/00を挿入していました
ということですが、このデータを取得して来た時に、「ERROR! : Value'0000-00-00' can not be represented as java.sql.Date」というエラーメッセージがセル中に表示されてはいないでしょうか。
JDBCドライバーの仕様では、日付値が「0000-00-00」だった場合、エラーが発生するようになっています。
MySQLの日付型列には
・insert into テーブル (id, 日付列) values(1,'0000-00-00') ゼロ値が入る
・受付不能な値の場合、ゼロ値「0000-00-00」が入る
・(MySQLのテーブル日付列がNULL可の場合)
insert into テーブル (id, 日付列) values(1,NULL) NULL値が入るようになっています。
そして、MySQL内の日付の値が「0000-00-00」だった場合、MZPlatformではエラーメッセージを取得しセル内に表示しますので、このメッセージ取得以降MZPlatform上の列型は「文字列型」となってしまいます。
日付型列を取得しても何故か文字列型となっているのは、上記が原因ではないでしょうか。取得直後にデータを[テーブル格納変数]に入れた場合など、目視して確認できなかったことが考えられます。
回避方法としては
@値が無い場合には、日付列を「NULL可」として「values(NULL)」として頂く方が良いかと思います。
Aどうしても現状のままゼロ値を入れる場合には、データベースの接続URLへオプション文字列を付けます。
例えばSampleフォルダ内のアプリケーション「データベースアクセス_3(機能拡張版).mzax」にはデータベース名の後ろに
『?useUnicode=true&characterEncoding=SJIS』と書いてありますが、後ろに続けて『&zeroDateTimeBehavior=round』としてみて下さい。
(『useUnicode=・・・』オプションを使っていない場合には、データベース名に続けて『?zeroDateTimeBehavior=round』だけで結構です)
これで「0000-00-00」の値を取得する際には、最も近い整数「0001-01-01」に変換され、MZPlatform上では日付型値、日付列型となります。
上記オプションを付けても検索の際の条件句は「where 日付列='0000-00-00'」(NULL値は含まない)、「where 日付列<>'0000-00-00'」(NULL値も含み排除される)で変わりません。
2)
>0002/11/30と変な日付に変換されてしまいます
これはMySQLのDate型の列に「2時11分30秒」つまり「2:11:30」の値を入れた時に起こります。
どこか日付型データに関するコンポーネント([日付入力フィールド]、[日時選択]、[カレンダー]など)から時刻の情報を拾ってきてしまってはいないでしょうか。
MySQLの列がDate型(日付のみ)の場合、日付の情報だけ入れれば良いのですが、MZPlatform上で日付型のデータを扱う際には、日付と時間両方の情報を持っていますので、何らかの理由で日付の情報が抜け落ち、時間の情報のだけが追加されてしまったなどが考えられます。
Q135-3:
やはり0000/00/00の表示をしたいと思いますので、接続URLへオプション文字を追加することを試したいと思います。
ひとつ言葉足らずで、誤解を招いたかもしれませんが、'0002/11/30'は調べてみると、エクセルファイルで'0000/00/00'で入力したカラムがSampleのエクセルファイルアクセスで読み込むと'0002/11/30'で読み出され、これをMySQLへ日付型としてストアしているものでした。
従って、エクセルファイルアクセスでの読み込み時の変換と考えられます。
このSample programで’0000/00/00'を'0000/00/00'(または0000-00-00)で読み込む方法はありますでしょうか?
A135-3:
@[EXCEL] ⇒[MZPlatform]⇒[MySQL] とデータを格納し、また、[MySQL] ⇒[MZPlatform]へ表示する。
AMySQLへは[データベースアクセス]でinsert文でデータを追加する。
EXCELからは[EXCELファイルアクセス]でデータを入力する。
@、Aを前提とします。
MZPlatformの[テーブル]にはjavaに基づく仕様により、日付型列にゼロ値「0000/00/00」を入れることはできません。
「0002/11/30」になる理由ですが、javaでは年月日の値が「0」の場合、一つ前の値として扱われますので、0年0月0日→紀元前1年0月0日→紀元前2年12月0日→紀元前2年11月30日となります。
前回、的外れな回答になってしまい大変失礼致しました。
値「0000/00/00」をEXCELに入れておきたいということでしたら、
[EXCEL] ⇒[MZPlatform]の時点では、この[テーブル]は文字列型のままで宜しいかと思います。
insert文も「insert into テーブル (id, 日付列) values(1,'0000/00/00')」という形式で構いません。
MySQLへのデータ追加に問題はないと思います。
[MySQL] ⇒[MZPlatform]の際ですが、「zeroDateTimeBehavior」のオプションを接続文字列に追加して頂く方法を前回ご紹介しました。
a.)『&zeroDateTimeBehavior=round』とし、[テーブル]日付型列内でのゼロ値の表示は「0001/01/01」となる
他に考えられる方法としては以下があります。
b.)『&zeroDateTimeBehavior=convertToNull』とし、[テーブル]日付型列内でのゼロ値の表示はNULL値(何も表示されない)となる(*パッチファイルが必要)
c.)a,bどちらかの接続オプションで取得した値を、処理を追加し「0000/00/00」に変更して表示する。但し日付型列のままでは「0000/00/00」は設定できないので、該当列は文字列型に変更する
質問2のご連絡では[テーブル]の列型の変更を色々お試し頂いたとのことでしたが、MySQLから取得したデータが文字列型になる原因はJDBCでのゼロ値の取得と推測されますので、基本的には[テーブル]の列型の変更や[日付入力フィールド]の使用は必要なくなったかと考えております。
但しMZPlatform上の[テーブル]での表示も「0000/00/00」としたい場合には「c」で示した方法になります。
「b」については、現在のところ[データベースアクセス]コンポーネント内でエラーが発生する不具合が見つかっていますので、お試しになる場合には、お手数でもご連絡ください。修正パッチファイルをお送りします。
ご連絡:
実際の使用、煩雑さを考え、0001/01/01の日付で処理することに致しました。アプリケーションでは0001/01/01は入力なしと判断するステップを挿入、処理しております。お手数をお掛けしましたが、現状は期待どおりに動いております。