pyorient icon indicating copy to clipboard operation
pyorient copied to clipboard

Invalid queries generated with `filter` functionality in v1.5.5

Open obi1kenobi opened this issue 8 years ago • 5 comments

With pyorient version 1.5.5,

graph.query(Animal).filter(Animal.name == 'dog').one()

causes a syntactically invalid query to be generated and sent to the database:

SELECT FROM Animal WHERE name = dog LIMIT 2

Note the absence of quotes around dog in the generated query. This happens because the filter_string method in query.py, called by build_wheres in the same file, does not seem to encode values correctly. Note how build_wheres uses the PropertyEncoder to encode values correctly, but filter_string does not.

This is both a functionality issue and also perhaps a security issue, since raw unescaped user-generated strings are passed to the database. All a malicious user would have to do is pass a quoted string followed by a malicious command, and it would be game over.

obi1kenobi avatar Aug 08 '17 22:08 obi1kenobi

Thanks @obi1kenobi. I notice this is resolved in the develop branch.

@Ostico I think we're reaching a point where releasing 1.5.6 makes sense (after making a decision about https://github.com/mogui/pyorient/pull/249, since it affects the same interface as the recent SSL support changes)

1.5.6 will contain quite an impressive set of improvements:

General Improvements

  • Make OrientRecordLink hashable, collection methods on OrientRecord.
  • Preliminary SSL support
  • Fix Groovy scripts for Python 3.6
  • Decoding of embedded RidBags

OGM Improvements

  • Substantial optimizations; pre-built queries, traversals, and batches (with token substitution), caching and dynamic link resolution
  • Query pretty-printing
  • Wrappers around SQL UPDATE, TRAVERSE
  • Support for sequences
  • Batch Improvements: Branching syntax, ability to collect() multiple query results

TropicalPenguin avatar Aug 09 '17 06:08 TropicalPenguin

Thanks for the update -- develop does seem to have fixed the problem!

However, it seems that 1.5.6 has made a breaking change with how the database schema is represented, and I keep getting errors like:

out_link = getattr(cls, 'out', None)
from_cls = out_link.linked_to if out_link else None

E     AttributeError: 'ChainableWhat' object has no attribute 'linked_to'

In this case, cls is a relationship class corresponding to an edge type in the database. I'm not really sure how to use ChainableWhat or how to get the type of vertex the edge is linked to. I'd appreciate any pointers in the right direction.

obi1kenobi avatar Aug 09 '17 18:08 obi1kenobi

I see. in_ and out were added as members of pyorient.ogm.edge.Edge, to enable building queries against the values of properties on an edge's in-vertex and out-vertex. I think this was a reasonable design choice but I'm all ears to the contrary.

This would have the effect of shadowing schema properties accessible through it's pyorient.ogm.element.GraphElement base.

I presume these particular schema properties would still be accessible through the _props (dict) member of cls, in your example. Ugly, but hopefully the need is less frequent than the SELECT/Query use case.

TropicalPenguin avatar Aug 10 '17 07:08 TropicalPenguin

Hm...maybe those members could be removed from the instance object.

TropicalPenguin avatar Aug 10 '17 08:08 TropicalPenguin

Hi @obi1kenobi I took a look and I'm not totally clear how you're getting that problem. If there is a schema property with that name, it shouldn't be shadowed by the Edge members. I'd expect it to work the other way 'round.

Do you have a small example script to demonstrate?

TropicalPenguin avatar Aug 12 '17 11:08 TropicalPenguin