Skip to content

[BUG]: Postgres expression not work with RawValue #15064

Open
@galliroberto

Description

@galliroberto

Describe the bug
RawValue does not work when I try to run it in Model or phql, using postgis.
I try to insert new location using postgis expression like ST_Transform(ST_SetSRID(ST_MakePoint(longitude, latitude),4326),2163)

I get error

"SQLSTATE[XX000]: Internal error: 7 ERROR:  parse error - invalid geometry",
        "HINT:  \"ST\" <-- parse error at position 2 within geometry"

beacause is not evaluated like expression but like string, so geometry get back error

To Reproduce
Steps to reproduce the behavior:

  • install timescale with postgis
  • enable extension for timescale e postgis
  • run migration to create table
  • try to run phql

Provide minimal script to reproduce the issue
migration:

class CreaDeviceTableMigration_101 extends Migration
{
    public function morph()
    {
        $this->morphTable('device', [
            'columns' => [
                new Column('id', [
                    'type' => Column::TYPE_VARCHAR,
                    'size' => 36,
                    'notNull' => true,
                    'first' => true,
                ]),
                new Column('latitude', [
                    'type' => Column::TYPE_DECIMAL,
                    'size' => 20,
                    'scale' => 6,
                    'after' => 'id',
                ]),
                new Column('longitude', [
                    'type' => Column::TYPE_DECIMAL,
                    'size' => 20,
                    'scale' => 6,
                    'after' => 'latitude',
                ]),
                new Column('occurred_at', [
                    'type' => Column::TYPE_TIMESTAMP,
                    'notNull' => true,
                    'after' => 'longitude',
                ]),
            ],
            'indexes' => [
                new Index('device.PRIMARY', [
                    'id',
                ]),
                new Index('device.occurred_at', [
                    'occurred_at',
                ]),
            ],
        ]);
    }

    public function afterCreateTable()
    {
        /*
         * ALTER TABLE device ADD COLUMN latitude geometry(POINT,2163);
         * ALTER TABLE device ADD COLUMN longitude geometry(POINT,2163);
         *
         * ALTER TABLE table_name
         *  ALTER COLUMN column_name_1 [SET DATA] TYPE new_data_type,
         *  ALTER COLUMN column_name_2 [SET DATA] TYPE new_data_type,
         *  ...;
         */
        $trasformaInHyperTable = "SELECT create_hypertable('device', 'occurred_at');";
        $this->getConnection()->execute($trasformaInHyperTable);

        $pointPostgis = "ALTER TABLE device ADD COLUMN location geometry(POINT,2163);";
        $this->getConnection()->execute($pointPostgis);
    }

    /**
     * Run the migrations
     *
     * @return void
     */
    public function up()
    {
    }

    /**
     * Reverse the migrations
     *
     * @return void
     */
    public function down()
    {
    }
}

model:

class DeviceModel extends Model
{
    /**
     * @Primary
     * @Identity
     * @Column(type='string', nullable=false)
     */
    public string $id;
    /**
     * @Column(type='double', nullable=false)
     */
    public float $lat;
    /**
     * @Column(type='double', nullable=false)
     */
    public float $lng;
    /**
     * @Column(type='string', nullable=true)
     */
    public string $location;
    /**
     * @Column(type='datetime', nullable=false)
     */
    public string $occurredAt;

    public function initialize()
    {
        $this->setSource('device');
    }
}

phql1:

$phql = /** @lang text */
    "
        INSERT INTO RdP\Infrastructure\Domain\PhalconModel\DeviceModel 
        (id, longitude, latitude, [location], occurred_at) 
        VALUES 
        (:id:, :latitude:, :longitude:, :location:, :occurred_at:)
    ";

$modelsManager = \Phalcon\Di::getDefault()->getModelsManager();
$query = $modelsManager->executeQuery($phql, [
    "id"   => $id->toString(),
    "latitude" => $device->geo()->latitude(),
    "longitude" => $device->geo()->longitude(),
    "location" => new \Phalcon\Db\RawValue('ST_Transform(ST_SetSRID(ST_MakePoint(10, 20),4326),2163)'),
    "occurred_at" => $occurredAt->format('Y-m-d H:i:s'),
]);

phql2:

$phql = /** @lang text */
    "
        INSERT INTO RdP\Infrastructure\Domain\PhalconModel\DeviceModel 
        (id, longitude, latitude, [location], occurred_at) 
        VALUES 
        (:id:, :latitude:, :longitude:, ST_Transform(ST_SetSRID(ST_MakePoint(:longitude:, :latitude:),4326),2163), :occurred_at:)
    ";

$modelsManager = \Phalcon\Di::getDefault()->getModelsManager();
$query = $modelsManager->executeQuery($phql, [
    "id" => $id->toString(),
    "latitude" => $device->geo()->latitude(),
    "longitude" => $device->geo()->longitude(),
    "occurred_at" => $occurredAt->format('Y-m-d H:i:s'),
]);
    

Expected behavior
If I run plain query go fine

$sqlPersistenzaDevice = sprintf("INSERT INTO device (id, longitude, latitude, location, occurred_at) VALUES ('%s', %f, %f, ST_Transform(ST_SetSRID(ST_MakePoint(%f, %f),4326),2163), '%s')",
            $id->toString(), $device->geo()->longitude(), $device->geo()->latitude(), $device->geo()->longitude(), $device->geo()->latitude(),
            $occurredAt->format('Y-m-d H:i:s'));

        try {
            $isPersisted = $this->connection->execute($sqlPersistenzaDevice);
        } catch (Exception $e) {
            $errors['device'] = ['sql' => $e->getMessage()];
            throw new RilevamentiValidationException('', 0, $errors);
        }

Screenshots
If applicable, add screenshots to help explain your problem.

Details

  • Phalcon version: 4.0.5
  • PHP Version: 7.4.2
  • Operating System: debian
  • Installation type: Compiling from source
  • Zephir version (if any):
  • Server: Nginx
  • Database: Postgres (timescale + postgis)

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    Status

    Backlog

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions