sql >> データベース >  >> RDS >> Mysql

JPAMySQLデータベースに間違った日付を保存する

    tl; dr

    JPA2.2 を使用します java.timeのサポートに対して 。

    Javaで日付のみのクラスを使用して、SQLで日付のみの値を操作します。

    LocalDate                           // Represent a date-only, without a time-of-day and without a time zone.
    .now(                               // Get today's date…
        ZoneId.of( "Africa/Tunis" )     // …as seen in the wall-clock time used by the people of a particular region.
    )                                   // Returns a `LocalDate` object.
    .plusMonths( 1 )                    // Returns another `LocalDate` object, per immutable objects pattern.
    

    java.time

    JPA 2.2 最新のjava.timeをサポートするようになりました クラス。 Joda-Timeを使用する必要はもうありません。

    しないでください java.sql.Dateを使用します 。 そのクラスはふり 日付のみを表しますが、 java.util.Date から継承するというひどい設計上の決定のため、実際には時刻がUTCに設定されています。 (名前にもかかわらず、日付を表します 時刻および UTC自体のオフセットはゼロです)。これらのレガシークラスはひどい惨めな混乱です。 Sun、Oracle、およびJCPコミュニティはすべて、数年前にJSR310の採用によりこれらのクラスをあきらめました。そうすべきです。

    LocalDate

    LocalDate classは、時刻やタイムゾーン のない日付のみの値を表します。 または offset-from-UTC 。

    タイムゾーンは、日付を決定する上で非常に重要です。いつでも、日付はゾーンごとに世界中で異なります。たとえば、パリフランス の深夜0時から数分 モントリオールケベック ではまだ「昨日」の新しい日です 。

    タイムゾーンが指定されていない場合、JVMは現在のデフォルトのタイムゾーンを暗黙的に適用します。そのデフォルトはいつでも変更 実行時(!)であるため、結果が異なる場合があります。引数として、希望する/予想されるタイムゾーンを明示的に指定することをお勧めします。重要な場合は、ユーザーにゾーンを確認してください。

    適切なタイムゾーン名 を指定します Continent / Regionの形式で 、 America / Montrealなど 、アフリカ/カサブランカ 、または Pacific / Auckland EST などの2〜4文字の略語は絶対に使用しないでください。 またはIST ではないので 真のタイムゾーン、標準化されておらず、一意でもありません(!)。

    ZoneId z = ZoneId.of( "America/Montreal" ) ;  
    LocalDate today = LocalDate.now( z ) ;
    

    JVMの現在のデフォルトのタイムゾーンを使用する場合は、それを要求し、引数として渡します。省略した場合、コードは読みにくくなり、デフォルトを使用するつもりだったのか、多くのプログラマーのように問題に気付いていなかったのかがわかりません。

    ZoneId z = ZoneId.systemDefault() ;  // Get JVM’s current default time zone.
    

    または、日付を指定します。 1月から12月までは、1〜12の番号を付けて、月を番号で設定できます。

    LocalDate ld = LocalDate.of( 1986 , 2 , 23 ) ;  // Years use sane direct numbering (1986 means year 1986). Months use sane numbering, 1-12 for January-December.
    

    または、 Month<を使用することをお勧めします。 / code> 1年の各月に1つずつ、事前定義された列挙型オブジェクト。ヒント:これらの Monthを使用してください コードをより自己文書化し、有効な値を確保し、型安全性も同様です。 YearMonth

    LocalDate ld = LocalDate.of( 1986 , Month.FEBRUARY , 23 ) ;
    

    日時の計算

    どうやらあなたは1つの日付から始めて、1か月後に日付範囲として取得したいと考えています。

    LocalDate monthLater = ld.plusMonths( 1 ) ;
    

    JDBC 4.2

    JDBC 4.2以降、JDBCドライバーはいくつかのキー java.timeをサポートする必要があります。 LocalDateなどのクラス 。

    日付範囲

    ThreeTen-Extraについては以下のリンクに注意してください 。 LocalDateRangeが見つかる場合があります 日付範囲で多くの作業を行う場合に便利なクラスがあります。

    java.timeについて

    java.time フレームワークはJava8以降に組み込まれています。これらのクラスは、厄介な古いレガシー に取って代わります。 javaなどの日時クラス。 util.Date カレンダー 、&​​ SimpleDateFormat

    詳細については、Oracleチュートリアルを参照してください。 。そして、StackOverflowで多くの例と説明を検索してください。仕様は JSR310 です。 。

    Joda-Time プロジェクト、現在メンテナンスモードjava.time<への移行をアドバイスします/ a> クラス。

    java.timeを交換できます データベースに直接オブジェクトを追加します。 JDBCドライバー を使用します JDBC4.2 に準拠 またはそれ以降。文字列は必要ありません。java.sql。*も必要ありません。 クラス。

    java.timeクラスはどこで入手できますか?

    ThreeTen-Extra プロジェクトは、追加のクラスでjava.timeを拡張します。このプロジェクトは、java.timeに将来追加される可能性のある試験場です。ここには、間隔 YearWeek YearQuarter 、および詳細



    1. SQLServerデータベースの増大に応じてデータ収集を自動化する方法

    2. MYSQLI-WHEREIN配列

    3. MariaDB JSON_QUOTE()の説明

    4. SQLite-JOINステートメント