github.com/dolthub/go-mysql-server@v0.18.0/sql/expression/function/spatial/st_srid_test.go (about) 1 // Copyright 2020-2021 Dolthub, Inc. 2 // 3 // Licensed under the Apache License, Version 2.0 (the "License"); 4 // you may not use this file except in compliance with the License. 5 // You may obtain a copy of the License at 6 // 7 // http://www.apache.org/licenses/LICENSE-2.0 8 // 9 // Unless required by applicable law or agreed to in writing, software 10 // distributed under the License is distributed on an "AS IS" BASIS, 11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 // See the License for the specific language governing permissions and 13 // limitations under the License. 14 15 package spatial 16 17 import ( 18 "testing" 19 20 "github.com/stretchr/testify/require" 21 22 "github.com/dolthub/go-mysql-server/sql" 23 "github.com/dolthub/go-mysql-server/sql/expression" 24 "github.com/dolthub/go-mysql-server/sql/types" 25 ) 26 27 func TestSRID(t *testing.T) { 28 t.Run("select unspecified SRID is 0", func(t *testing.T) { 29 require := require.New(t) 30 f, err := NewSRID(expression.NewLiteral(types.Point{X: 1, Y: 2}, types.PointType{})) 31 require.NoError(err) 32 33 v, err := f.Eval(sql.NewEmptyContext(), nil) 34 require.NoError(err) 35 require.Equal(uint32(0), v) 36 }) 37 38 t.Run("select specified SRID is 0", func(t *testing.T) { 39 require := require.New(t) 40 f, err := NewSRID(expression.NewLiteral(types.Point{SRID: 0, X: 1, Y: 2}, types.PointType{})) 41 require.NoError(err) 42 43 v, err := f.Eval(sql.NewEmptyContext(), nil) 44 require.NoError(err) 45 require.Equal(uint32(0), v) 46 }) 47 48 t.Run("select specified SRID is 4326", func(t *testing.T) { 49 require := require.New(t) 50 f, err := NewSRID(expression.NewLiteral(types.Point{SRID: 4326, X: 1, Y: 2}, types.PointType{})) 51 require.NoError(err) 52 53 v, err := f.Eval(sql.NewEmptyContext(), nil) 54 require.NoError(err) 55 require.Equal(uint32(4326), v) 56 }) 57 58 t.Run("change SRID to 0", func(t *testing.T) { 59 require := require.New(t) 60 f, err := NewSRID(expression.NewLiteral(types.Point{SRID: 4326, X: 1, Y: 2}, types.PointType{}), 61 expression.NewLiteral(0, types.Int32)) 62 require.NoError(err) 63 64 v, err := f.Eval(sql.NewEmptyContext(), nil) 65 require.NoError(err) 66 require.Equal(types.Point{SRID: 0, X: 1, Y: 2}, v) 67 }) 68 69 t.Run("change SRID to 4326", func(t *testing.T) { 70 require := require.New(t) 71 f, err := NewSRID(expression.NewLiteral(types.Point{SRID: 0, X: 123.4, Y: 56.789}, types.PointType{}), 72 expression.NewLiteral(4326, types.Int32)) 73 require.NoError(err) 74 75 v, err := f.Eval(sql.NewEmptyContext(), nil) 76 require.NoError(err) 77 require.Equal(types.Point{SRID: 4326, X: 123.4, Y: 56.789}, v) 78 }) 79 80 t.Run("change SRID to invalid 1234", func(t *testing.T) { 81 require := require.New(t) 82 f, err := NewSRID(expression.NewLiteral(types.Point{SRID: 0, X: 123.4, Y: 56.789}, types.PointType{}), 83 expression.NewLiteral(1234, types.Int32)) 84 require.NoError(err) 85 86 _, err = f.Eval(sql.NewEmptyContext(), nil) 87 require.Error(err) 88 }) 89 90 t.Run("invalid number of arguments, 0", func(t *testing.T) { 91 require := require.New(t) 92 _, err := NewSRID() 93 require.Error(err) 94 }) 95 96 t.Run("change SRID of linestring to 4326", func(t *testing.T) { 97 require := require.New(t) 98 f, err := NewSRID(expression.NewLiteral(types.LineString{Points: []types.Point{{X: 1, Y: 2}, {X: 3, Y: 4}}}, types.LineStringType{}), 99 expression.NewLiteral(4326, types.Int32)) 100 require.NoError(err) 101 102 v, err := f.Eval(sql.NewEmptyContext(), nil) 103 require.NoError(err) 104 require.Equal(types.LineString{SRID: 4326, Points: []types.Point{{SRID: 4326, X: 1, Y: 2}, {SRID: 4326, X: 3, Y: 4}}}, v) 105 }) 106 107 t.Run("change SRID of polygon to 4326", func(t *testing.T) { 108 require := require.New(t) 109 f, err := NewSRID(expression.NewLiteral(types.Polygon{Lines: []types.LineString{{Points: []types.Point{{X: 0, Y: 0}, {X: 0, Y: 1}, {X: 1, Y: 1}, {X: 0, Y: 0}}}}}, types.PolygonType{}), 110 expression.NewLiteral(4326, types.Int32)) 111 require.NoError(err) 112 113 v, err := f.Eval(sql.NewEmptyContext(), nil) 114 require.NoError(err) 115 require.Equal(types.Polygon{SRID: 4326, Lines: []types.LineString{{SRID: 4326, Points: []types.Point{{SRID: 4326, X: 0, Y: 0}, {SRID: 4326, X: 0, Y: 1}, {SRID: 4326, X: 1, Y: 1}, {SRID: 4326, X: 0, Y: 0}}}}}, v) 116 }) 117 118 t.Run("select srid of geometry with inner point", func(t *testing.T) { 119 require := require.New(t) 120 121 f, err := NewSRID(expression.NewLiteral(types.Point{X: 1, Y: 2}, types.GeometryType{})) 122 require.NoError(err) 123 124 v, err := f.Eval(sql.NewEmptyContext(), nil) 125 require.NoError(err) 126 require.Equal(uint32(0), v) 127 }) 128 129 t.Run("select srid of geometry with inner linestring", func(t *testing.T) { 130 require := require.New(t) 131 132 f, err := NewSRID(expression.NewLiteral(types.LineString{Points: []types.Point{{X: 1, Y: 2}, {X: 3, Y: 4}}}, types.GeometryType{})) 133 require.NoError(err) 134 135 v, err := f.Eval(sql.NewEmptyContext(), nil) 136 require.NoError(err) 137 require.Equal(uint32(0), v) 138 }) 139 140 t.Run("select srid of geometry with inner polygon", func(t *testing.T) { 141 require := require.New(t) 142 143 f, err := NewSRID(expression.NewLiteral(types.Polygon{Lines: []types.LineString{{Points: []types.Point{{X: 0, Y: 0}, {X: 0, Y: 1}, {X: 1, Y: 1}, {X: 0, Y: 0}}}}}, types.GeometryType{})) 144 require.NoError(err) 145 146 v, err := f.Eval(sql.NewEmptyContext(), nil) 147 require.NoError(err) 148 require.Equal(uint32(0), v) 149 }) 150 151 t.Run("select srid of geometry with inner multipoint", func(t *testing.T) { 152 require := require.New(t) 153 154 f, err := NewSRID(expression.NewLiteral(types.MultiPoint{Points: []types.Point{{X: 1, Y: 2}, {X: 3, Y: 4}}}, types.GeometryType{})) 155 require.NoError(err) 156 157 v, err := f.Eval(sql.NewEmptyContext(), nil) 158 require.NoError(err) 159 require.Equal(uint32(0), v) 160 }) 161 162 t.Run("select srid of geometry with inner multilinestring", func(t *testing.T) { 163 require := require.New(t) 164 165 f, err := NewSRID(expression.NewLiteral(types.MultiLineString{Lines: []types.LineString{{Points: []types.Point{{X: 0, Y: 0}, {X: 0, Y: 1}, {X: 1, Y: 1}, {X: 0, Y: 0}}}}}, types.GeometryType{})) 166 require.NoError(err) 167 168 v, err := f.Eval(sql.NewEmptyContext(), nil) 169 require.NoError(err) 170 require.Equal(uint32(0), v) 171 }) 172 173 t.Run("select srid of geometry with inner multipolygon", func(t *testing.T) { 174 require := require.New(t) 175 line := types.LineString{Points: []types.Point{{X: 0, Y: 0}, {X: 1, Y: 0}, {X: 1, Y: 1}, {X: 0, Y: 0}}} 176 poly := types.Polygon{Lines: []types.LineString{line}} 177 f, err := NewSRID(expression.NewLiteral(types.MultiPolygon{Polygons: []types.Polygon{poly}}, types.GeometryType{})) 178 require.NoError(err) 179 180 v, err := f.Eval(sql.NewEmptyContext(), nil) 181 require.NoError(err) 182 require.Equal(uint32(0), v) 183 }) 184 185 t.Run("change srid of geometry with inner point to 4326", func(t *testing.T) { 186 require := require.New(t) 187 188 f, err := NewSRID(expression.NewLiteral(types.Point{X: 1, Y: 2}, types.GeometryType{}), 189 expression.NewLiteral(4326, types.Int32)) 190 require.NoError(err) 191 192 v, err := f.Eval(sql.NewEmptyContext(), nil) 193 require.NoError(err) 194 require.Equal(types.Point{SRID: 4326, X: 1, Y: 2}, v) 195 }) 196 197 t.Run("change srid of geometry with inner linestring to 4326", func(t *testing.T) { 198 require := require.New(t) 199 200 f, err := NewSRID(expression.NewLiteral(types.LineString{Points: []types.Point{{X: 1, Y: 2}, {X: 3, Y: 4}}}, types.GeometryType{}), 201 expression.NewLiteral(4326, types.Int32)) 202 require.NoError(err) 203 204 v, err := f.Eval(sql.NewEmptyContext(), nil) 205 require.NoError(err) 206 require.Equal(types.LineString{SRID: 4326, Points: []types.Point{{SRID: 4326, X: 1, Y: 2}, {SRID: 4326, X: 3, Y: 4}}}, v) 207 }) 208 209 t.Run("change srid of geometry with inner polygon to 4326", func(t *testing.T) { 210 require := require.New(t) 211 212 f, err := NewSRID(expression.NewLiteral(types.Polygon{Lines: []types.LineString{{Points: []types.Point{{X: 0, Y: 0}, {X: 0, Y: 1}, {X: 1, Y: 1}, {X: 0, Y: 0}}}}}, types.GeometryType{}), 213 expression.NewLiteral(4326, types.Int32)) 214 require.NoError(err) 215 216 v, err := f.Eval(sql.NewEmptyContext(), nil) 217 require.NoError(err) 218 require.Equal(types.Polygon{SRID: 4326, Lines: []types.LineString{{SRID: 4326, Points: []types.Point{{SRID: 4326, X: 0, Y: 0}, {SRID: 4326, X: 0, Y: 1}, {SRID: 4326, X: 1, Y: 1}, {SRID: 4326, X: 0, Y: 0}}}}}, v) 219 }) 220 221 t.Run("change srid of geometry with inner multipoint to 4326", func(t *testing.T) { 222 require := require.New(t) 223 224 f, err := NewSRID(expression.NewLiteral(types.MultiPoint{Points: []types.Point{{X: 1, Y: 2}, {X: 3, Y: 4}}}, types.GeometryType{}), 225 expression.NewLiteral(4326, types.Int32)) 226 require.NoError(err) 227 228 v, err := f.Eval(sql.NewEmptyContext(), nil) 229 require.NoError(err) 230 require.Equal(types.MultiPoint{SRID: 4326, Points: []types.Point{{SRID: 4326, X: 1, Y: 2}, {SRID: 4326, X: 3, Y: 4}}}, v) 231 }) 232 233 t.Run("change srid of geometry with inner multilinestring", func(t *testing.T) { 234 require := require.New(t) 235 236 f, err := NewSRID(expression.NewLiteral(types.MultiLineString{Lines: []types.LineString{{Points: []types.Point{{X: 0, Y: 0}, {X: 0, Y: 1}, {X: 1, Y: 1}, {X: 0, Y: 0}}}}}, types.GeometryType{}), 237 expression.NewLiteral(4326, types.Int32)) 238 require.NoError(err) 239 240 v, err := f.Eval(sql.NewEmptyContext(), nil) 241 require.NoError(err) 242 require.Equal(types.MultiLineString{SRID: 4326, Lines: []types.LineString{{SRID: 4326, Points: []types.Point{{SRID: 4326, X: 0, Y: 0}, {SRID: 4326, X: 0, Y: 1}, {SRID: 4326, X: 1, Y: 1}, {SRID: 4326, X: 0, Y: 0}}}}}, v) 243 }) 244 245 t.Run("change srid of geometry with inner multipolygon", func(t *testing.T) { 246 require := require.New(t) 247 line := types.LineString{Points: []types.Point{{X: 0, Y: 0}, {X: 1, Y: 0}, {X: 1, Y: 1}, {X: 0, Y: 0}}} 248 poly := types.Polygon{Lines: []types.LineString{line}} 249 f, err := NewSRID(expression.NewLiteral(types.MultiPolygon{SRID: 0, Polygons: []types.Polygon{poly}}, types.GeometryType{}), 250 expression.NewLiteral(4326, types.Int32)) 251 require.NoError(err) 252 253 v, err := f.Eval(sql.NewEmptyContext(), nil) 254 require.NoError(err) 255 line2 := types.LineString{SRID: 4326, Points: []types.Point{{SRID: 4326, X: 0, Y: 0}, {SRID: 4326, X: 1, Y: 0}, {SRID: 4326, X: 1, Y: 1}, {SRID: 4326, X: 0, Y: 0}}} 256 poly2 := types.Polygon{SRID: 4326, Lines: []types.LineString{line2}} 257 require.Equal(types.MultiPolygon{SRID: 4326, Polygons: []types.Polygon{poly2}}, v) 258 }) 259 260 t.Run("change srid of geometry with inner geometry collection", func(t *testing.T) { 261 require := require.New(t) 262 point := types.Point{X: 1, Y: 2} 263 line := types.LineString{Points: []types.Point{{X: 1, Y: 2}, {X: 3, Y: 4}}} 264 poly := types.Polygon{Lines: []types.LineString{{Points: []types.Point{{X: 0, Y: 0}, {X: 1, Y: 1}, {X: 1, Y: 0}, {X: 0, Y: 0}}}}} 265 g := types.GeomColl{Geoms: []types.GeometryValue{ 266 point, 267 line, 268 poly, 269 }} 270 f, err := NewSRID(expression.NewLiteral(g, types.GeometryType{}), 271 expression.NewLiteral(4326, types.Int32)) 272 require.NoError(err) 273 274 v, err := f.Eval(sql.NewEmptyContext(), nil) 275 require.NoError(err) 276 point2 := types.Point{SRID: 4326, X: 1, Y: 2} 277 line2 := types.LineString{SRID: 4326, Points: []types.Point{{SRID: 4326, X: 1, Y: 2}, {SRID: 4326, X: 3, Y: 4}}} 278 poly2 := types.Polygon{SRID: 4326, Lines: []types.LineString{{SRID: 4326, Points: []types.Point{{SRID: 4326, X: 0, Y: 0}, {SRID: 4326, X: 1, Y: 1}, {SRID: 4326, X: 1, Y: 0}, {SRID: 4326, X: 0, Y: 0}}}}} 279 g2 := types.GeomColl{SRID: 4326, Geoms: []types.GeometryValue{ 280 point2, 281 line2, 282 poly2, 283 }} 284 require.Equal(g2, v) 285 }) 286 287 t.Run("return type with one argument", func(t *testing.T) { 288 require := require.New(t) 289 f, err := NewSRID(expression.NewLiteral(types.Point{X: 1, Y: 2}, types.PointType{})) 290 require.NoError(err) 291 292 v, err := f.Eval(sql.NewEmptyContext(), nil) 293 require.NoError(err) 294 295 typ := f.Type() 296 _, _, err = typ.Convert(v) 297 require.NoError(err) 298 }) 299 300 t.Run("return type with two arguments", func(t *testing.T) { 301 require := require.New(t) 302 f, err := NewSRID(expression.NewLiteral(types.LineString{Points: []types.Point{{X: 1, Y: 2}, {X: 3, Y: 4}}}, types.LineStringType{}), 303 expression.NewLiteral(4326, types.Int32)) 304 require.NoError(err) 305 306 v, err := f.Eval(sql.NewEmptyContext(), nil) 307 require.NoError(err) 308 309 typ := f.Type() 310 _, _, err = typ.Convert(v) 311 require.NoError(err) 312 }) 313 }