Search code examples
python-3.xorientdborientdb-2.1pyorient

Finding all properties for a schema-less vertex class


I have a class Node extends V. I add instances to Node with some set of document type information provided. I want to query the OrientDB database and return some information from Node; to display this in a formatted way I want a list of all possible field names (in my application, there are currently 115 field names, only one of which is a property used as an index)

To do this in pyorient, the only solution I found so far is (client is the name of the database handle):

count = client.query("SELECT COUNT(*) FROM Node")[0].COUNT
node_records = client.query("SELECT FROM Node LIMIT {0}".format(count))
node_key_list = set([])
for node in node_records:
   node_key_list |= node.oRecordData.keys()

I figured that much out pretty much through trial and error. It isn't very efficient or elegant. Surely there must be a way to have the database return a list of all possible fields for a class or any other document-type object. Is there a simple way to do this through either pyorient or the SQL commands?


Solution

  • I tried your case with this dataset:

    enter image description here

    And this is the structure of my class TestClass:

    enter image description here

    As you can see from my structure only name, surname and timeStamp have been created in schema-full mode, instead nameSchemaLess1 and nameSchemaLess1 have been inserted into the DB in schema-less mode.

    After having done that, you could create a Javascript function in OrientDB Studio or Console (as explained here) and subsequently you can recall it from pyOrient by using a SQL command.

    The following posted function retrieves all the fields names of the class TestClass without duplicates:

    Javascript function:

    var g = orient.getGraph();
    
    var fieldsList = [];
    var query = g.command("sql", "SELECT FROM TestClass");
    for (var x = 0; x < query.length; x++){
      var fields = query[x].getRecord().fieldNames();
      for (var y = 0; y < fields.length; y++) {
        if (fieldsList == false){
          fieldsList.push(fields[y]);
        } else {
          var fieldFound = false;
          for (var z = 0; z < fieldsList.length; z++){
            if (fields[y] == fieldsList[z]){
              fieldFound = true;
              break;
            }
          }
          if (fieldFound != true){
            fieldsList.push(fields[y]);
          }
        }
      }
    }
    return fieldsList;
    

    pyOrient code:

    import pyorient
    
    
    db_name = 'TestDatabaseName'
    
    print("Connecting to the server...")
    client = pyorient.OrientDB("localhost", 2424)
    session_id = client.connect("root", "root")
    print("OK - sessionID: ", session_id, "\n")
    
    if client.db_exists(db_name, pyorient.STORAGE_TYPE_PLOCAL):
        client.db_open(db_name, "root", "root")
        functionCall = client.command("SELECT myFunction() UNWIND myFunction")
        for idx, val in enumerate(functionCall):
            print("Field name:  " + val.myFunction)
    
    client.db_close()
    

    Output:

    Connecting to the server...
    OK - sessionID:  54 
    
    Field name:  name
    Field name:  surname
    Field name:  timeStamp
    Field name:  out_testClassEdge
    Field name:  nameSchemaLess1
    Field name:  in_testClassEdge
    Field name:  nameSchemaLess2
    

    As you can see all of the fields names, both schema-full and schema-less, have been retrieved.

    Hope it helps