View Full Version : Bug: Using structure variables for filters
aGorilla
04-18-06, 10:33 PM
This code:
<MvFILTER NAME="{l.table}" FILTER_TYPE="variable" FILTER="l.this:filter">
Give's me this (rather cryptic) error message:
C:\...\Temp\\mva00000001:1017: AE_311: Duplicate string identifier "s_0"
Delete the ':' in 'l.this:filter', and it works. A minor bug, but an annoying one.
truXoft
04-18-06, 11:15 PM
Although unrelated, I have to warn you that using local variables in filters is quite unsafe, since the filter still be active even if the local variable is no more available. Basically, I strongly advice using only global variables in filters.
aGorilla
04-18-06, 11:36 PM
Funny thing is, I've been avoiding globals like the plague. In this case, it's only a temp filter for a loader/display function (ie: I'm going to kill the filter before the function exits). In most other cases, I pass them in by VAR, which is my own little 'private' global :)
aGorilla
04-19-06, 12:36 AM
Although unrelated, I have to warn you that using local variables in filters is quite unsafe, since the filter still be active even if the local variable is no more available. Basically, I strongly advice using only global variables in filters.
I'm not seeing this, so I decided to run a test. It seems that the filter is only evaluated once. Here's my test, let me know if I'm missing something.
<MvCREATE NAME="FilterTest" DATABASE="filtertest.dbf"
FIELDS="key CHAR(10), val CHAR(10)">
<MvMAKEINDEX NAME="FilterTest" INDEXFILE="filtertest.mvx"
EXPRESSION="{FilterTest.d.key}" FLAGS="unique">
<MvASSIGN NAME="FilterTest.d.key" VALUE="abc">
<MvASSIGN NAME="FilterTest.d.val" VALUE="1">
<MvADD NAME="FilterTest">
<MvASSIGN NAME="FilterTest.d.key" VALUE="def">
<MvASSIGN NAME="FilterTest.d.val" VALUE="2">
<MvADD NAME="FilterTest">
<MvASSIGN NAME="FilterTest.d.key" VALUE="ghi">
<MvASSIGN NAME="FilterTest.d.val" VALUE="3">
<MvADD NAME="FilterTest">
<MvCOMMENT> let's run through it in the wild. </MvCOMMENT>
<MvGO NAME="FilterTest" ROW="top">
<MvWHILE EXPR="{NOT FilterTest.d.EOF}">
<MvEVAL EXPR="{'Debug wild: ' $ FilterTest.d.key $ '<br>'}">
<MvSKIP NAME="FilterTest" ROWS="1">
</MvWHILE>
<MvFUNCTION NAME="test1" STANDARDOUTPUTLEVEL="">
<MvCOMMENT> now we add a filter </MvCOMMENT>
<MvASSIGN NAME="l.filter" VALUE="FilterTest.d.key EQ 'def'">
<MvFILTER NAME="FilterTest" FILTER_TYPE="variable" FILTER="l.filter">
<MvCOMMENT> and run through it again </MvCOMMENT>
<MvGO NAME="FilterTest" ROW="top">
<MvWHILE EXPR="{NOT FilterTest.d.EOF}">
<MvEVAL EXPR="{'Debug test 1: ' $ FilterTest.d.key $ '<br>'}">
<MvSKIP NAME="FilterTest" ROWS="1">
</MvWHILE>
</MvFUNCTION>
<MvFUNCTION NAME="test2" STANDARDOUTPUTLEVEL="">
<MvCOMMENT> l.filter is gone now, but just in case. </MvCOMMENT>
<MvASSIGN NAME="l.filter" VALUE="I'm not the filter you thought I was.">
<MvGO NAME="FilterTest" ROW="top">
<MvWHILE EXPR="{NOT FilterTest.d.EOF}">
<MvEVAL EXPR="{'Debug test 2: ' $ FilterTest.d.key $ '<br>'}">
<MvSKIP NAME="FilterTest" ROWS="1">
</MvWHILE>
</MvFUNCTION>
<MvFUNCTION NAME="test3" STANDARDOUTPUTLEVEL="">
<MvCOMMENT> just for thoroughness. </MvCOMMENT>
<MvASSIGN NAME="l.filter" VALUE="Neither am I.">
<MvGO NAME="FilterTest" ROW="top">
<MvWHILE EXPR="{NOT FilterTest.d.EOF}">
<MvEVAL EXPR="{'Debug test 3: ' $ FilterTest.d.key $ '<br>'}">
<MvSKIP NAME="FilterTest" ROWS="1">
</MvWHILE>
</MvFUNCTION>
<MvEVAL EXPR="{test1()}">
<MvEVAL EXPR="{test2()}">
<MvEVAL EXPR="{test3()}">
<MvCLOSE NAME="FilterTest">
Here's the output:
Debug wild: abc
Debug wild: def
Debug wild: ghi
Debug test 1: def
Debug test 2: def
Debug test 3: def
Edit: After more testing, I see what you mean. Since you replied to my post where I was using a local variable _as_ the filter -- and you had no idea what was in it, I assumed that's what you were talking about (always a dangerous thing to do). Apparently, that's quite safe. But yes, using a local variable _in_ a filter can change the output.
<MvCREATE NAME="FilterTest" DATABASE="filtertest.dbf"
FIELDS="key CHAR(10), val CHAR(10)">
<MvMAKEINDEX NAME="FilterTest" INDEXFILE="filtertest.mvx"
EXPRESSION="{FilterTest.d.key}" FLAGS="unique">
<MvASSIGN NAME="FilterTest.d.key" VALUE="abc">
<MvASSIGN NAME="FilterTest.d.val" VALUE="1">
<MvADD NAME="FilterTest">
<MvASSIGN NAME="FilterTest.d.key" VALUE="def">
<MvASSIGN NAME="FilterTest.d.val" VALUE="2">
<MvADD NAME="FilterTest">
<MvASSIGN NAME="FilterTest.d.key" VALUE="ghi">
<MvASSIGN NAME="FilterTest.d.val" VALUE="3">
<MvADD NAME="FilterTest">
<MvCOMMENT> let's run through it in the wild. </MvCOMMENT>
<MvGO NAME="FilterTest" ROW="top">
<MvWHILE EXPR="{NOT FilterTest.d.EOF}">
<MvEVAL EXPR="{'Debug wild: ' $ FilterTest.d.key $ '<br>'}">
<MvSKIP NAME="FilterTest" ROWS="1">
</MvWHILE>
<MvFUNCTION NAME="test1" STANDARDOUTPUTLEVEL="">
<MvCOMMENT> now we add a filter </MvCOMMENT>
<MvASSIGN NAME="l.key" VALUE="def">
<MvASSIGN NAME="l.filter" VALUE="FilterTest.d.key EQ l.key">
<MvFILTER NAME="FilterTest" FILTER_TYPE="variable" FILTER="l.filter">
<MvCOMMENT> and run through it again </MvCOMMENT>
<MvGO NAME="FilterTest" ROW="top">
<MvWHILE EXPR="{NOT FilterTest.d.EOF}">
<MvEVAL EXPR="{'Debug test 1: ' $ FilterTest.d.key $ '<br>'}">
<MvSKIP NAME="FilterTest" ROWS="1">
</MvWHILE>
</MvFUNCTION>
<MvFUNCTION NAME="test2" STANDARDOUTPUTLEVEL="">
<MvCOMMENT> l.filter is gone now, but just in case. </MvCOMMENT>
<MvASSIGN NAME="l.key" VALUE="abc">
<MvASSIGN NAME="l.filter" VALUE="I'm not the filter you thought I was.">
<MvGO NAME="FilterTest" ROW="top">
<MvWHILE EXPR="{NOT FilterTest.d.EOF}">
<MvEVAL EXPR="{'Debug test 2: ' $ FilterTest.d.key $ '<br>'}">
<MvSKIP NAME="FilterTest" ROWS="1">
</MvWHILE>
</MvFUNCTION>
<MvFUNCTION NAME="test3" STANDARDOUTPUTLEVEL="">
<MvCOMMENT> just for thoroughness. </MvCOMMENT>
<MvASSIGN NAME="l.key" VALUE="ghi">
<MvASSIGN NAME="l.filter" VALUE="Neither am I.">
<MvGO NAME="FilterTest" ROW="top">
<MvWHILE EXPR="{NOT FilterTest.d.EOF}">
<MvEVAL EXPR="{'Debug test 3: ' $ FilterTest.d.key $ '<br>'}">
<MvSKIP NAME="FilterTest" ROWS="1">
</MvWHILE>
</MvFUNCTION>
<MvEVAL EXPR="{test1()}">
<MvEVAL EXPR="{test2()}">
<MvEVAL EXPR="{test3()}">
<MvCLOSE NAME="FilterTest">
Output:
Debug wild: abc
Debug wild: def
Debug wild: ghi
Debug test 1: def
Debug test 2: abc
Debug test 3: ghi
vBulletin® v3.7.4, Copyright ©2000-2008, Jelsoft Enterprises Ltd.