deephaven / deephaven-core

Deephaven Community Core
Other
248 stars 79 forks source link

Python static method return values are unusable in columns #5045

Open chipkent opened 8 months ago

chipkent commented 8 months ago
from deephaven import empty_table

class C:
    def do_it(self, i) -> int:
        return i+1

    @staticmethod
    def get_c() -> 'C':
        return C()

t = empty_table(10).update(["CC = C.get_c()"])

t2 = t.update("X = CC.do_it(ii)")
r-Scheduler-Serial-1 | .c.ConsoleServiceGrpcImpl | Error running script: java.lang.RuntimeException: Error in Python interpreter:
Type: <class 'deephaven.dherror.DHError'>
Value: table update operation failed. : Cannot find method do_it(long) in class java.lang.Object
Traceback (most recent call last):
  File "/opt/deephaven/venv/lib/python3.10/site-packages/deephaven/table.py", line 913, in update
    return Table(j_table=self.j_table.update(*formulas))
RuntimeError: io.deephaven.engine.table.impl.select.FormulaCompilationException: Formula compilation error for: CC.do_it(ii)
    at io.deephaven.engine.table.impl.select.DhFormulaColumn.initDef(DhFormulaColumn.java:214)
    at io.deephaven.engine.table.impl.select.SwitchColumn.initDef(SwitchColumn.java:56)
    at io.deephaven.engine.table.impl.select.analyzers.SelectAndViewAnalyzer.create(SelectAndViewAnalyzer.java:115)
    at io.deephaven.engine.table.impl.select.analyzers.SelectAndViewAnalyzer.create(SelectAndViewAnalyzer.java:63)
    at io.deephaven.engine.table.impl.QueryTable.lambda$selectOrUpdate$30(QueryTable.java:1467)
    at io.deephaven.engine.table.impl.perf.QueryPerformanceRecorder.withNugget(QueryPerformanceRecorder.java:519)
    at io.deephaven.engine.table.impl.QueryTable.lambda$selectOrUpdate$31(QueryTable.java:1449)
    at io.deephaven.engine.table.impl.QueryTable.memoizeResult(QueryTable.java:3456)
    at io.deephaven.engine.table.impl.QueryTable.selectOrUpdate(QueryTable.java:1448)
    at io.deephaven.engine.table.impl.QueryTable.update(QueryTable.java:1426)
    at io.deephaven.engine.table.impl.QueryTable.update(QueryTable.java:106)
    at io.deephaven.api.TableOperationsDefaults.update(TableOperationsDefaults.java:94)
    at org.jpy.PyLib.executeCode(Native Method)
    at org.jpy.PyObject.executeCode(PyObject.java:138)
    at io.deephaven.engine.util.PythonEvaluatorJpy.evalScript(PythonEvaluatorJpy.java:73)
    at io.deephaven.integrations.python.PythonDeephavenSession.lambda$evaluate$1(PythonDeephavenSession.java:194)
    at io.deephaven.util.locks.FunctionalLock.doLockedInterruptibly(FunctionalLock.java:51)
    at io.deephaven.integrations.python.PythonDeephavenSession.evaluate(PythonDeephavenSession.java:194)
    at io.deephaven.engine.util.AbstractScriptSession.lambda$evaluateScript$0(AbstractScriptSession.java:147)
    at io.deephaven.engine.context.ExecutionContext.lambda$apply$0(ExecutionContext.java:149)
    at io.deephaven.engine.context.ExecutionContext.apply(ExecutionContext.java:160)
    at io.deephaven.engine.context.ExecutionContext.apply(ExecutionContext.java:148)
    at io.deephaven.engine.util.AbstractScriptSession.evaluateScript(AbstractScriptSession.java:147)
    at io.deephaven.engine.util.DelegatingScriptSession.evaluateScript(DelegatingScriptSession.java:84)
    at io.deephaven.engine.util.ScriptSession.evaluateScript(ScriptSession.java:102)
    at io.deephaven.server.console.ConsoleServiceGrpcImpl.lambda$executeCommand$4(ConsoleServiceGrpcImpl.java:175)
    at io.deephaven.server.session.SessionState$ExportBuilder.lambda$submit$3(SessionState.java:1474)
    at io.deephaven.server.session.SessionState$ExportObject.doExport(SessionState.java:974)
    at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:539)
    at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
    at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1136)
    at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:635)
    at io.deephaven.server.runner.scheduler.SchedulerModule$ThreadFactory.lambda$newThread$0(SchedulerModule.java:78)
    at org.jpy.PyLib.callAndReturnObject(Native Method)
    at org.jpy.PyObject.call(PyObject.java:449)
    at io.deephaven.server.console.python.DebuggingInitializer.lambda$createInitializer$0(DebuggingInitializer.java:30)
    at java.base/java.lang.Thread.run(Thread.java:840)
caused by io.deephaven.engine.table.impl.lang.QueryLanguageParser$QueryLanguageParseException: 

Having trouble with the following expression:
Full expression           : CC.do_it(ii)
Expression having trouble : 
Exception type            : io.deephaven.engine.table.impl.lang.QueryLanguageParser$ParserResolutionFailure
Exception message         : Cannot find method do_it(long) in class java.lang.Object

    at io.deephaven.engine.table.impl.lang.QueryLanguageParser.getMethod(QueryLanguageParser.java:626)
    at io.deephaven.engine.table.impl.lang.QueryLanguageParser.visit(QueryLanguageParser.java:2303)
    at io.deephaven.engine.table.impl.lang.QueryLanguageParser.visit(QueryLanguageParser.java:132)
    at com.github.javaparser.ast.expr.MethodCallExpr.accept(MethodCallExpr.java:116)
    at io.deephaven.engine.table.impl.lang.QueryLanguageParser.<init>(QueryLanguageParser.java:273)
    at io.deephaven.engine.table.impl.lang.QueryLanguageParser.<init>(QueryLanguageParser.java:224)
    at io.deephaven.engine.table.impl.lang.QueryLanguageParser.<init>(QueryLanguageParser.java:198)
    at io.deephaven.engine.table.impl.select.codegen.FormulaAnalyzer.getCompiledFormula(FormulaAnalyzer.java:133)
    at io.deephaven.engine.table.impl.select.DhFormulaColumn.initDef(DhFormulaColumn.java:194)
    ... 36 more

Line: 915
Namespace: update
File: /opt/deephaven/venv/lib/python3.10/site-packages/deephaven/table.py
Traceback (most recent call last):
  File "<string>", line 13, in <module>
  File "/opt/deephaven/venv/lib/python3.10/site-packages/deephaven/table.py", line 915, in update

    at org.jpy.PyLib.executeCode(Native Method)
    at org.jpy.PyObject.executeCode(PyObject.java:138)
    at io.deephaven.engine.util.PythonEvaluatorJpy.evalScript(PythonEvaluatorJpy.java:73)
    at io.deephaven.integrations.python.PythonDeephavenSession.lambda$evaluate$1(PythonDeephavenSession.java:194)
    at io.deephaven.util.locks.FunctionalLock.doLockedInterruptibly(FunctionalLock.java:51)
    at io.deephaven.integrations.python.PythonDeephavenSession.evaluate(PythonDeephavenSession.java:194)
    at io.deephaven.engine.util.AbstractScriptSession.lambda$evaluateScript$0(AbstractScriptSession.java:147)
    at io.deephaven.engine.context.ExecutionContext.lambda$apply$0(ExecutionContext.java:149)
    at io.deephaven.engine.context.ExecutionContext.apply(ExecutionContext.java:160)
    at io.deephaven.engine.context.ExecutionContext.apply(ExecutionContext.java:148)
    at io.deephaven.engine.util.AbstractScriptSession.evaluateScript(AbstractScriptSession.java:147)
    at io.deephaven.engine.util.DelegatingScriptSession.evaluateScript(DelegatingScriptSession.java:84)
    at io.deephaven.engine.util.ScriptSession.evaluateScript(ScriptSession.java:102)
    at io.deephaven.server.console.ConsoleServiceGrpcImpl.lambda$executeCommand$4(ConsoleServiceGrpcImpl.java:175)
    at io.deephaven.server.session.SessionState$ExportBuilder.lambda$submit$3(SessionState.java:1474)
    at io.deephaven.server.session.SessionState$ExportObject.doExport(SessionState.java:974)
    at java.base/java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:539)
    at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
    at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1136)
    at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:635)
    at io.deephaven.server.runner.scheduler.SchedulerModule$ThreadFactory.lambda$newThread$0(SchedulerModule.java:78)
    at org.jpy.PyLib.callAndReturnObject(Native Method)
    at org.jpy.PyObject.call(PyObject.java:449)
    at io.deephaven.server.console.python.DebuggingInitializer.lambda$createInitializer$0(DebuggingInitializer.java:30)
    at java.base/java.lang.Thread.run(Thread.java:840)

This code seems to run, but the tables are not rendering.

def get_c2() -> C:
    return C()

t3 = empty_table(10).update("CC = get_c2()")
t4 = t3.update("XX = CC.do_it(ii)")
chipkent commented 8 months ago

More looking at this seems to indicate that the problem may be with the python class methods in the query string.

jmao-denver commented 7 months ago

This change makes it work.

t2 = t.update("X = (int)((PyObject)CC).do_it(ii)")

The reason: we can't support auto-conversion of Python values for class methods (static or not) yet (#3121).