001: /*
002: * Copyright (c) 1998 - 2005 Versant Corporation
003: * All rights reserved. This program and the accompanying materials
004: * are made available under the terms of the Eclipse Public License v1.0
005: * which accompanies this distribution, and is available at
006: * http://www.eclipse.org/legal/epl-v10.html
007: *
008: * Contributors:
009: * Versant Corporation - initial API and implementation
010: */
011: package com.versant.core.jdbc.sql.conv;
012:
013: import com.versant.core.jdbc.JdbcConverter;
014: import com.versant.core.jdbc.JdbcConverterFactory;
015: import com.versant.core.jdbc.JdbcTypeRegistry;
016: import com.versant.core.jdbc.metadata.JdbcColumn;
017:
018: import java.sql.PreparedStatement;
019: import java.sql.SQLException;
020: import java.sql.ResultSet;
021: import java.util.Locale;
022:
023: import javax.jdo.JDOFatalDataStoreException; //todo: appears only in throws-clause
024:
025: import com.versant.core.common.BindingSupportImpl;
026:
027: /**
028: * This converter converts Locale objects to and from SQL. It assumes that
029: * the Locale is stored in a column compatible with ResultSet.getString and
030: * PreparedStatement.setString. The Locale is stored as a 4 or 6 character
031: * String (lang + country [+ variant]).
032: * @keep-all
033: */
034: public class LocaleConverter extends JdbcConverterBase {
035:
036: public static class Factory extends NoArgJdbcConverterFactory {
037:
038: private LocaleConverter converter;
039:
040: /**
041: * Create a converter for col using args as parameters. Return null if
042: * no converter is required.
043: */
044: public JdbcConverter createJdbcConverter(JdbcColumn col,
045: Object args, JdbcTypeRegistry jdbcTypeRegistry) {
046: if (converter == null)
047: converter = new LocaleConverter();
048: return converter;
049: }
050:
051: }
052:
053: /**
054: * Get the value of col from rs at position index.
055: * @exception SQLException on SQL errors
056: * @exception JDOFatalDataStoreException if the ResultSet value is invalid
057: */
058: public Object get(ResultSet rs, int index, JdbcColumn col)
059: throws SQLException, JDOFatalDataStoreException {
060: String s = rs.getString(index);
061: if (s == null)
062: return null;
063: s = s.trim();
064: if (s.length() == 0)
065: return null;
066: try {
067: String lang = s.substring(0, 2);
068: String country = null;
069: if (s.length() > 2) {
070: country = s.substring(2, 4);
071: } else {
072: country = "";
073: }
074: String variant = null;
075: if (s.length() > 4) {
076: variant = s.substring(4, 6);
077: } else {
078: variant = "";
079: }
080: return new Locale(lang, country, variant);
081: } catch (IndexOutOfBoundsException x) {
082: throw BindingSupportImpl.getInstance()
083: .fatalDatastore(
084: "Invalid Locale value for " + col + ": '"
085: + s + "'", x);
086: }
087: }
088:
089: /**
090: * Set parameter index on ps to value (for col).
091: * @exception SQLException on SQL errors
092: * @exception JDOFatalDataStoreException if value is invalid
093: */
094: public void set(PreparedStatement ps, int index, JdbcColumn col,
095: Object value) throws SQLException,
096: JDOFatalDataStoreException {
097: if (value == null) {
098: ps.setNull(index, col.jdbcType);
099: } else {
100: Locale l = (Locale) value;
101: StringBuffer s = new StringBuffer();
102: s.append(l.getLanguage());
103: s.append(l.getCountry());
104: if (col.length >= 6) {
105: String v = l.getVariant();
106: if (v.length() == 0)
107: v = " ";
108: s.append(v);
109: }
110: ps.setString(index, s.toString());
111: }
112: }
113:
114: /**
115: * Get the type of our expected value objects (e.g. java.util.Locale
116: * for a converter for Locale's).
117: */
118: public Class getValueType() {
119: return Locale.class;
120: }
121:
122: }
|