MDSplus / mdsplus

The MDSplus data management system
https://mdsplus.org/
Other
71 stars 43 forks source link

Python thin-client error getting member ID numbers #1211

Closed lamorton closed 6 years ago

lamorton commented 6 years ago

I'm getting an error when trying to use the thin-client python interface to get the member IDs of a node ... I can get the number of members, and I can use the thick-client interface to the the member IDs. I've tried for a few different tree/shot combos.

import MDSplus as mds treename='activespec' shotNumber=204112 string='\activespec::TOP.MPTS.OUTPUT_DATA.BEST'

thin-client version

cx=mds.connection.Connection('skylark.pppl.gov') cx.openTree(treename,shotNumber) print cx.get('getnci(%s,"NUMBER_OF_MEMBERS")'%string)

prints 21

print cx.get('getnci(%s,"MEMBER_NIDS")'%string)

MdsException: %TREE-E-TreeNODATA, No data available for this node

thick-client version

spectree=mds.Tree('activespec',shotNumber) tsnode=spectree.getNode(string) print tsnode.member_nids

[897,895,918,920,921,923,913,914,915,917,241,896,927,929,924,925,77,278,36,912,75]

zack-vii commented 6 years ago

Hello lamorton, the problem might be that getnci(%s,"NUMBER_OF_MEMBERS") actually returns a ArrayOfNids not Ints. However, The thin client will try to convert every data into simple DATA types. arrays or scalars of atomic types or strings. this will cast a DATA() around the ArrayOfNids which will try to return the record of each member of the array. You would need to cast it to ArrayOfInt first which you can do by

GETNCI($,"NID_NUMBER")

in your case use:

'GETNCI(getnci(%s,"MEMBER_NIDS"),"NID_NUMBER")'%string

Let us know if this helped you out.

Cheers

Timo

lamorton commented 6 years ago

Thanks Timo, that did the trick. - Lucas

lamorton commented 6 years ago

Timo, a few more questions: (1) is there a way to find the name of each dimension of an array? (2) Is there a way to build & execute a function? For instance, if I wanted to get a list of NIDS and filter it on the server side before pulling the data from each of the nodes? I'm not sure that getMany is what I want, because I don't necessarily want the return value from every statement, only the last one.

(3) What distinguishes a child node from a member node? Is it just the '.' vs ':' separator in the path? Are parent nodes allowed to have data arrays associated with them, or only 'leafs' on the tree?

tfredian commented 6 years ago

Hi Lucas,

I'm not sure what you mean with your question about "the name of each dimension". There is no built-in MDSplus mechanism for naming dimensions.

Regarding question 2) there are a couple different solutions but may be complicated. You can define public tdi functions by doing a get with an expression such as: cnx.get('public fun myfun(args...){[statements;]... return(_ans);},myfun(args...)')

Another solution is to try using the mdsconnector module. It is a standalone remote MDSplus objects module which does everything via proxy objects on the server side. It requires ssh access to the server. This is a very new module and I hope to document it soon on the mdsplus web site.

pip install mdsconnector [--user]

...

import mdsconnector help(mdsconnector) c=mdsConnector('host') t=c.Tree('treename',shotnum)

essentially all the "thick client" objects are available but are just proxies to the real objects on the server side. You only retrieve the data from the server when you invoke methods that produce primitive data types such as int, float or numpy data items. This way you can execute various functions that get executed on the server and when you get to your final answer you can retrieve the data by implicitly using methods such as data() to retrieve numpy data types.

Hope this helps, Tom