Mailing List Archives
Authenticated access
|
|
|
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: [HTCondor-users] matchmaking with python bindings changes behavior depending on the imports
- Date: Fri, 16 Nov 2018 00:29:01 +0000
- From: Todd Tannenbaum <tannenba@xxxxxxxxxxx>
- Subject: Re: [HTCondor-users] matchmaking with python bindings changes behavior depending on the imports
On 11/15/2018 2:35 PM, Jose Caballero wrote:
> Hi,
> is this behavior expected?
>
>>>> import classad
>>>> c = classad.ClassAd()
>>>> c['foo'] = 5
>>>> req = classad.ClassAd()
>>>> req['Requirements'] = classad.ExprTree('foo > 0')
>>>> c.matches(req)
> False
>
>>>> import htcondor
>>>> c.matches(req)
> True
>
>
Hi Jose,
Yes, for better or worse, this is currently the expected behavior.
The explanation can be found by understanding the "old" vs "new" ClassAd semantics. Details on this can be found in the HTCondor Manual here:
http://htcondor.org/manual/v8.7/HTCondorsClassAdMechanism.html#x48-3990004.1.1
But in a nutshell, when you do 'import classad' on its own, you get "new" semantics. When you do 'import htcondor', you get "old" classad semantics, because HTCondor itself uses the old semantics. One difference between old and new classads that explains the behavior you see above is when expressions refer to ClassAd attributes. These attribute references work differently in Old ClassAds as compared with New ClassAds. In New ClassAds, an unscoped reference is looked for only in the local ClassAd. An unscoped reference is an attribute that does not have a MY. or TARGET. prefix. In Old classads, the reference will first be looked for in the MY ad, and if it is not found, then it will automatically also be looked for in the TARGET ad.
Some examples below to help explain via demonstrative code.
Hope the above and below help!
regards,
Todd
Example One. This shows the same result you got above. The issue here is 'foo' is only looked up in ad req:
In: import classad
c = classad.ClassAd()
c['foo'] = 5
req = classad.ClassAd()
req['Requirements'] = classad.ExprTree('foo > 0')
c.matches(req)
Out: False
Example Two. Here we explicitly scope foo to be target.foo, and now we get a match:
In: import classad
c = classad.ClassAd()
c['foo'] = 5
req = classad.ClassAd()
req['Requirements'] = classad.ExprTree('TARGET.foo > 0')
c.matches(req)
Out: True
Example Three. Because we import htcondor here, we will get the 'old' semantics which will first lookup
attribute foo in MY scope and then automatically lookup attribute foo in TARGET, resulting in
the True output:
In: import classad
import htcondor
c = classad.ClassAd()
c['foo'] = 5
req = classad.ClassAd()
req['Requirements'] = classad.ExprTree('foo > 0')
c.matches(req)
Out: True
Example Four. So this example is same as Example Three, but we first set config knob
STRICT_CLASSAD_EVALUATION=True (it defaults to False). As explained in the Manual section I listed
above, you can set config knob STRICT_CLASSAD_EVALUATION=True to tell HTCondor (and thus
the htcondor python package) to use 'new' style semantics instead of defaulting to the 'old' style.
In: import os
os.environ['_condor_STRICT_CLASSAD_EVALUATION']='True'
import classad
import htcondor
c = classad.ClassAd()
c['foo'] = 5
req = classad.ClassAd()
req['Requirements'] = classad.ExprTree('foo > 0')
c.matches(req)
Out: False