java.sql.SQLException: गलत स्ट्रिंग मान: '\ xF0 \ x9F \ x91 \ xBD \ xF0 \ x9F ...'


107

मेरे पास निम्नलिखित स्ट्रिंग मूल्य हैं: "वॉल-मार्ट ओबामा value"

मैं MySQL और Java का उपयोग कर रहा हूं।

मुझे निम्नलिखित अपवाद मिल रहे हैं: `java.sql.SQLException: गलत स्ट्रिंग मान: '\ xF0 \ x9F \ x91 \ xBD \ xF0 \ x9F ...'

यहां वह चर है जिसे मैं सम्मिलित करने का प्रयास कर रहा हूं:

var1 varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL`

मेरा जावा कोड जो "वॉलमार्ट ओबमा is" सम्मिलित करने की कोशिश कर रहा है, एक तैयार किया गया स्टैटेमेंट है। इसलिए मैं setString()विधि का उपयोग कर रहा हूं ।

ऐसा लगता है कि समस्या मानों की एन्कोडिंग है। मैं इसे कैसे ठीक करूं? पहले मैं डर्बी एसक्यूएल का उपयोग कर रहा था और मूल्यों Der बस दो sqaures समाप्त हो गया (मुझे लगता है कि यह अशक्त चरित्र का प्रतिनिधित्व है)

सभी मदद की बहुत सराहना की जाती है!


का डुप्लिकेट की तरह लगता है stackoverflow.com/questions/10957238/...
यहोशू डेविस

जब आप डेटाबेस बनाते हैं, तो आप चरित्र सेट और इस तरह से टकराव दे सकते हैं:CREATE DATABASE db_name CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;
मैक्स पेंग

जवाबों:


145

आपके पास क्या है EXTRATERRESTRIAL ALIEN (U+1F47D)और BROKEN HEART (U+1F494)जो मूल बहुभाषी विमान में नहीं हैं। उन्हें जावा में एक चार के रूप में भी नहीं दिखाया जा सकता है "👽💔".length() == 4। वे निश्चित रूप से अशक्त पात्र नहीं हैं और यदि आप उन फोंट का उपयोग नहीं कर रहे हैं जो उनका समर्थन करते हैं तो एक वर्ग को देखेंगे।

MySQL utf8केवल मूल बहुभाषी विमान का समर्थन करता है, और आपको utf8mb4इसके बजाय उपयोग करने की आवश्यकता है :

एक पूरक चरित्र के लिए, utf8 चरित्र को बिल्कुल भी संग्रहीत नहीं कर सकता है, जबकि utf8mb4 को इसे संग्रहीत करने के लिए चार बाइट्स की आवश्यकता होती है। चूंकि utf8 चरित्र को बिल्कुल भी संग्रहीत नहीं कर सकता है, इसलिए आपके पास utf8 कॉलम में कोई भी अनुपूरक वर्ण नहीं हैं और आपको MySQL के पुराने संस्करणों से utf8 डेटा को अपग्रेड करते समय वर्ण परिवर्तित करने या डेटा खोने के बारे में चिंता करने की आवश्यकता नहीं है।

तो इन पात्रों का समर्थन करने के लिए, आपका MySQL 5.5+ होना चाहिए और आपको utf8mb4हर जगह उपयोग करने की आवश्यकता है। कनेक्शन एन्कोडिंग की जरूरत है utf8mb4, चरित्र सेट की आवश्यकता है utf8mb4और समतलीकरण की आवश्यकता है utf8mb4। जावा के लिए यह अभी भी है "utf-8", लेकिन MySQL को एक अंतर की आवश्यकता है।

मैं नहीं जानता कि आप किस ड्राइवर का उपयोग कर रहे हैं, लेकिन कनेक्शन सेटसेट को सेट करने के लिए ड्राइवर अज्ञेयवादी तरीका क्वेरी भेजने के लिए है:

SET NAMES 'utf8mb4'

संबंध बनाने के ठीक बाद।

कनेक्टर / J के लिए यह भी देखें :

14.14: मैं 4-बाइट UTF8, utf8mb4 को कनेक्टर / J के साथ कैसे उपयोग कर सकता हूं?

कनेक्टर / J के साथ 4-बाइट UTF8 का उपयोग करने के लिए mySQL सर्वर को character_set_server = utf8mb4 से कॉन्फ़िगर करें। कनेक्टर / J तब उस सेटिंग का उपयोग करेगा, जब तक कि कनेक्शन स्ट्रिंग में वर्ण संकेतन सेट नहीं किया गया हो । यह वर्ण सेट के ऑटोडेटेक्शन के बराबर है।

अपने कॉलम और डेटाबेस को भी समायोजित करें:

var1 varchar(255) CHARACTER SET utf8mb4 COLLATE utf8mb4_general_ci NOT NULL

फिर, आपके MySQL संस्करण को utf8mb4 समर्थन के लिए अपेक्षाकृत अद्यतित होना चाहिए।


मेरी अन्य संबंधित पोस्ट देखें: stackoverflow.com/questions/13748170/… । यदि आप इसका उत्तर दे सकते हैं, तो आपने इस प्रश्न का उत्तर भी दिया होगा। अन्य पोस्ट में मेरे द्वारा किए गए कार्यों का अधिक विवरण है।
कोडकिंगप्लसप्लस

1
@CodeKingPlusPlus ने अपने डेटाबेस में सब कुछ बदल दिया है utf8mb4, ऐसा लगता है कि आप अभी भी उपयोग कर रहे हैं utf8_general_ci..
Esailija

1
कनेक्टर / जे के साथ "सेट नाम" न करें: dev.mysql.com/doc/connector-j/en/… Do not issue the query set names with Connector/J, as the driver will not detect that the character set has changed, and will continue to use the character set detected during the initial connection setup.
bcoughlan

1
यदि आप अपने DB को बदलने की गड़बड़ी से निपटने के बजाय केवल BMP के बाहर के पात्रों से छुटकारा पाना चाहते हैं, तो यहां देखें: stackoverflow.com/questions/4035562/…
Indigenuity

2
मेरे पास एक ही समस्या है, ऊपर दिए गए चरणों का पालन किया गया लेकिन तब तक हल नहीं किया गया जब तक कि C- \ ProgramData \ MySQL \ MySQL सर्वर 5.7 \ my.ini
fattah.safa

16

सभी के लिए, 4 बाइट्स की आवश्यकता वाले प्रतीकों को सहेजने के लिए आपको चरचर-सेट और समतलीकरण अपडेट करने की आवश्यकता है utf8mb4:

  1. डेटाबेस तालिका / स्तंभ: alter table <some_table> convert to character set utf8mb4 collate utf8mb4_unicode_ci
  2. डेटाबेस सर्वर कनेक्शन ( देखें )

# 2 के लिए मेरे विकास पर मैं सर्वर शुरू करते समय कमांड लाइन पर पैरामीटर सेट करना पसंद करता हूं: mysqld --character-set-server=utf8mb4 --collation-server=utf8mb4_unicode_ci


btw, कनेक्टर / J के साथ व्यवहार पर ध्यान दें SET NAMES 'utf8mb4':

कनेक्टर / J के साथ क्वेरी सेट नाम जारी न करें, क्योंकि ड्राइवर यह पता नहीं लगाएगा कि चरित्र सेट बदल गया है, और प्रारंभिक कनेक्शन सेटअप के दौरान पहचाने गए वर्ण सेट का उपयोग करना जारी रखेगा।

और characterEncodingकनेक्शन url में पैरामीटर सेट करने से बचें क्योंकि यह कॉन्फ़िगर किए गए सर्वर एन्कोडिंग को ओवरराइड करेगा:

क्लाइंट साइड पर स्वचालित रूप से पता लगाए गए एन्कोडिंग को ओवरराइड करने के लिए, सर्वर से कनेक्ट करने के लिए उपयोग किए गए URL में वर्णक संपत्ति का उपयोग करें।


15

अजीब तरह से, मुझे लगता है कि निकाला जा रहा है पाया &characterEncoding=UTF-8सेJDBC url इसी तरह के मुद्दों के साथ मेरे लिए चाल किया गया ।

मेरे गुणों के आधार पर,

jdbc_url=jdbc:mysql://localhost:3306/dbName?useUnicode=true

मुझे लगता है कि यह @Esailija ने जो कहा है, उसका समर्थन करता है, अर्थात मेरा MySQL, जो कि वास्तव में 5.5 है, अपने UTF-8 एन्कोडिंग के अपने पसंदीदा स्वाद का पता लगा रहा है।

(ध्यान दें, मैं जावा कोड के InputStreamरूप UTF-8में पढ़ रहा हूं , जो संभवतः चोट नहीं करता है) को भी निर्दिष्ट कर रहा हूं ...


शायद useUnicode=trueजरूरत भी नहीं है? मेरे मामले में काम करने वाली एकमात्र चीज character_set_server=utf8mb4सर्वर (आरडीएस पैरामीटर समूह) पर विश्व स्तर पर स्थापित हो रही है और जेडडीबीसी यूआरएल में कोई भी पात्र नहीं है
यहोशू डेविस

6

मैंने अपनी समस्या को कैसे हल किया।

मैं था

?useUnicode=true&amp;characterEncoding=UTF-8

मेरे हाइबरनेट jdbc कनेक्शन url में और मैंने स्ट्रिंग डेटाटाइप को डेटाबेस में लॉन्गटेक्स्ट में बदल दिया, जो कि पहले था।


Greate अगर आपको उस कॉलम को अनुक्रमित करने और उसके अपेक्षाकृत छोटे होने की आवश्यकता नहीं है, लेकिन मैं अपने सभी कॉलमों के लिए इस ट्रिक को कर सकता हूं
Shareef

3

useUnicode=true&amp;characterEncoding=UTF-8अपने jdbc url पर लाइन को जोड़ें ।

आपके मामले में UTF-8एन्कोडिंग का उपयोग करके डेटा नहीं भेजा जा रहा है ।


मैं इसे कैसे जोड़ूं? मेरे संबंध में स्ट्रिंग? मैं Netbeans का उपयोग कर रहा हूँ अगर वह मदद करता है।
कोडकप्लसप्लस

आप कनेक्शन कैसे बना रहे हैं?
JHS

DriverManager.getConnection ("jdbc: mysql: // localhost: #### / [dbName]", [उपयोगकर्ता नाम], [पासवर्ड]);
CodeKingPlusPlus

इसे इस तरह करें - DriverManager.getConnection ("jdbc: mysql: // localhost: #### / [dbName]; यू यूनिकोड = ट्रू & amp; characterEncoding; यूटीएफ -8", [उपयोगकर्ता नाम], [पासवर्ड]);
जेएचएस

1
स्क्रैच कि, मैं भूल गया '?' लेकिन अब मैं मूल पोस्ट के समान त्रुटि ...
कोडिंगप्लसप्लस 22

3

मैंने एक ही मुद्दे का सामना किया और प्रत्येक कॉलम के लिए utf8_general_ci को Collation सेट करके इसे हल किया ।


2

मुझे लगता है कि MySQL का मानना ​​है कि यह मान्य UTF8 पाठ नहीं है। मैंने एक ही कॉलम डेफिनिशन (mysql क्लाइंट कनेक्शन भी UTF8 था) के साथ एक टेस्ट टेबल पर एक इंसर्ट करने की कोशिश की और हालांकि यह इंसर्ट किया, जो डेटा मैंने MySQL CLI क्लाइंट के साथ-साथ JDBC से प्राप्त किया और जो मान सही ढंग से प्राप्त नहीं हुए। यह सुनिश्चित करने के लिए कि UTF8 ने सही तरीके से काम किया, मैंने ओबमा के लिए "o" के बजाय "ö" डाला:

johan@maiden:~$ mysql -vvv test < insert.sql 
--------------
insert into utf8_test values(_utf8 "walmart öbama 👽💔")
--------------

Query OK, 1 row affected, 1 warning (0.12 sec)

johan@maiden:~$ file insert.sql 
insert.sql: UTF-8 Unicode text

के साथ परीक्षण करने के लिए छोटा जावा आवेदन:

package test.sql;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.ResultSet;

public class Test
{

    public static void main(String[] args)
    {
        System.out.println("test string=" + "walmart öbama 👽💔");
        String url = "jdbc:mysql://hostname/test?useUnicode=true&characterEncoding=UTF-8";
        try
        {
            Class.forName("com.mysql.jdbc.Driver").newInstance();
            Connection c = DriverManager.getConnection(url, "username", "password");
            PreparedStatement p = c.prepareStatement("select * from utf8_test");
            p.execute();
            ResultSet rs = p.getResultSet();
            while (!rs.isLast())
            {
                rs.next();
                String retrieved = rs.getString(1);
                System.out.println("retrieved=\"" + retrieved + "\"");

            }
        }
        catch (Exception e)
        {
            e.printStackTrace();
        }
    }

}

आउटपुट:

johan@appel:~/workspaces/java/javatest/bin$ java test.sql.Test
test string=walmart öbama 👽💔
retrieved="walmart öbama "

इसके अलावा, मैंने JDBC कनेक्शन के साथ एक ही इन्सर्ट करने की कोशिश की है और यह वही अपवाद फेंक रहा है जो आपको मिल रहा है। मेरा मानना ​​है कि यह एक MySQL बग है। शायद ऐसी स्थिति के बारे में पहले से ही एक बग रिपोर्ट है ..


वैसे, आपके स्ट्रिंग में वर्ण OSX पर फ़ायरफ़ॉक्स और क्रोम दोनों में सही ढंग से दिखाई नहीं देते हैं। वे मेरे iTerm आवेदन में सही ढंग से दिखाई देते हैं। मुझे लगता है कि यह फ़ॉन्ट निर्भर है।
फ्रेडेक

1

मुझे एक ही तरह की समस्या थी और सभी वर्णों के खिलाफ ध्यान से जाने और यह देखने के बाद कि वे सभी सही थे, मुझे एहसास हुआ कि मेरी कक्षा में जो भी संपत्ति थी, उसे @ जॉइनॉल्यूमेंट (javax .presistence; hibernate) के बजाय @ कॉलम के रूप में एनोटेट किया गया था; यह सब कुछ तोड़ रहा था।


1

निष्पादित

show VARIABLES like "%char%”;

अगर utf8mb4 नहीं है तो कैरेक्टर-सेट-सर्वर खोजें।

इसे अपने my.cnf में सेट करें, जैसे

vim /etc/my.cnf

एक पंक्ति जोड़ें

character_set_server = utf8mb4

आखिरी बार mysql को पुनः आरंभ करें


1
character_set_serverविकल्प है, नहींcharacter-set-server
अरुण एसआर

0

यह सेटिंग useOldUTF8Behavior = true ने मेरे लिए ठीक काम किया। इसने कोई गलत स्ट्रिंग त्रुटियां नहीं दीं, लेकिन इसने विशेष चरित्रों जैसे Ã को कई पात्रों में बदल दिया और डेटाबेस में सहेज लिया।

ऐसी स्थितियों से बचने के लिए, मैंने इस संपत्ति को JDBC पैरामीटर से हटा दिया और इसके बजाय अपने कॉलम के डेटाटाइप को BLOB में बदल दिया। यह सही काम किया।


क्या आप कृपया अपने उत्तर में अधिक डीटेल जोड़ सकते हैं? (कोड, कमेंट इत्यादि)
aBnormaLz

-2

इसके अलावा, डेटा प्रकार varchar या पाठ की बूँद स्थापित का उपयोग कर सकते हैं।


आप नहीं चाहते कि
ECostello
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.