sql >> Database >  >> RDS >> PostgreSQL

Hoe org.postgresql.geometric.PGpoint toe te wijzen aan Hibernate Type

Eerst en vooral denk ik dat GEOMETRY gegevenstypen worden ondersteund door Hibernate Spatial , maar als dat niet het geval is, kunt u altijd een aangepast slaapstandtype en een aangepast slaapstanddialect definiëren.

Ik had een soortgelijk probleem bij het beheren van een POINT kolom die geografische punten bevatte.

Ik heb een PostgisDialect . aangemaakt class die PostgreSQL9Dialect . uitbreidde , waar u het nieuwe gegevenstype op deze manier registreert

public PostgisDialect() {
    registerColumnType(Types.BINARY, "geography");        
}

in jouw geval zou je het type registreren als "geometrie"

dan definieert u een GeometryType class die UserType implementeert

Vreemd genoeg is het proces van het schrijven van een aangepast Hibernate-type niet een van de meest gedocumenteerde functies, dus ik zal hier plakken wat ik heb geschreven om mijn PointType te definiëren. Voor de andere methoden in de interface laat ik ze UnsupportedOperationException throw gooien

public class PointType implements UserType{
private static final Type[] PROPERTY_TYPES = new Type[] { 
    StringType.INSTANCE };
public String[] getPropertyNames() {
     return new String[] {"point"};   }

public Type[] getPropertyTypes() {
    return PROPERTY_TYPES;
}


public Class returnedClass() {
   return Point.class;
}

public boolean equals(Object o, Object o1) throws HibernateException {
    if((o instanceof Point && o1 instanceof Point) == false)
        return false;
    Point p1 = (Point) o;
    Point p2 = (Point) o1;
    boolean equal = ((p1.getX() == p2.getX()) && (p1.getY() == p2.getY()));
    return equal;


}   

public Object nullSafeGet(ResultSet rs, String[] strings, SessionImplementor si, Object o) throws HibernateException, SQLException {
// the method which gets the data from the column and converts it to a Point using       BinaryParser
   BinaryParser bp = new BinaryParser();       
   try{          
      String binaryString = rs.getString(strings[0]);
       return bp.parse(binaryString);
   }
   catch(Exception ex){ return null;}

}

public void nullSafeSet(PreparedStatement ps, Object o, int i, SessionImplementor si) throws HibernateException, SQLException {
    Point p = (Point) o ;
    if(p!=null){
       BinaryWriter bw = new BinaryWriter();
       ps.setObject(i,bw.writeBinary(p));      
    }

public Object deepCopy(Object o) throws HibernateException {
    Point p = (Point) o;        
    Point newPoint = null;
    if(p!=null){
        newPoint = new Point(p.x, p.y);
        newPoint.setSrid(p.getSrid());
    }
    return newPoint;

}

public boolean isMutable() {
    return true;
}


public int[] sqlTypes() {
    return new int[]{Types.BINARY};
}    

}

enkele snelle opmerkingen:nullSafeSet en nullSafeGet schrijven en lezen respectievelijk de waarden van/naar de database met behulp van de BinaryWriter/BinaryParser-objecten.

Nadat u dit alles hebt gedefinieerd, annoteert u zo uw modelklasse zodat deze uw aangepaste type gebruikt

@Column(name="point")
@Type(type="eu.enricorampazzosoluzioni.incidentpredicter.dataCopier.hibernate.types.PointType")
private Point point;

Last but not least moet u Hibernate vertellen om uw aangepaste dialect te gebruiken. Als u Spring gebruikt om uw sessiefabriek te definiëren, kunt u deze definiëren via hibernateProperties

<property name="hibernateProperties">
     <props>           
         <prop key="hibernate.dialect">eu.enricorampazzosoluzioni.incidentpredicter.dataCopier.hibernate.dialect.PostgisDialect</prop>            
     </props>
  </property>



  1. sqlalchemy postgresql waarbij int =string

  2. Gegevens importeren uit Microsoft SQL-bestand (.MDF) in MySQL

  3. mysql-tellingswoord in sql-syntaxis

  4. Transacties werken niet voor mijn MySQL DB