$regex
og MongoRegex (dvs. en BSON regex-type brugt i et lighedsmatch) understøtter kun matchning mod strenge, så du kan ikke bruge dem direkte med et ObjectId.
Med hensyn til dit sidste kodeeksempel, forsøgte du at bruge $where
i en MongoRegex-konstruktør:
$searchTermsAny[] = array(
$dataProps[$i] => new MongoRegex( '/'.$sRegex.'/i',
'$where: "this._id.toString().match(/'.$sRegex.'/i)"' )
);
MongoRegex
's konstruktør tager en enkelt streng (f.eks. /foo/i
), hvorfra det stammer mønsteret og flagene. $where
er beregnet til at blive brugt som en forespørgselsoperator på øverste niveau (ikke forbundet med noget feltnavn). Jeg følger ikke, hvad du laver med $dataProps[$i]
, men lad os antage, at du konstruerede en enkelt $where
forespørgsel for at matche en ObjectId's strengrepræsentation. Forespørgselsdokumentet vil se sådan ud:
{ $where: 'this._id.str.match(/00005/)' }
Bemærk, at jeg har adgang til str
egenskab her i stedet for at kalde toString()
. Det er fordi toString()
returnerer faktisk skalrepræsentationen af ObjectId. Du kan se dette ved at tjekke dens kilde i skallen:
> x = new ObjectId()
ObjectId("5409ddcfd95d6f6a2eb33e7f")
> x.toString
function (){
return "ObjectId(" + tojson(this.str) + ")";
}
Også, hvis du blot tjekker, om der findes en understreng i _id
s hex-repræsentation, vil du måske bruge indexOf()
(med en != -1
sammenligning) i stedet for match()
med et regex.
Når det er sagt, ved hjælp af $where
er generelt en dårlig idé, hvis du ikke kombinerer det med yderligere forespørgselskriterier, som kan bruge et indeks. Dette er fordi $where
aktiverer JavaScript-fortolkeren for hvert dokument, der tages i betragtning i resultatsættet. Hvis du kombinerer det med andre, mere selektive kriterier, kan MongoDB bruge et indeks og indsnævre de dokumenter, som det skal evaluere med $where
; du har dog en dårlig tid, hvis du bruger $where
og scanning af mange dokumenter eller en bordscanning i værste fald.
Du er sandsynligvis bedre af at oprette et andet felt i hvert dokument, der indeholder hex-strengrepræsentationen af _id
. Derefter kan du indeksere det felt og forespørge efter det ved hjælp af et regex. De ikke-forankrede regex-forespørgsler vil stadig være en smule ineffektive (se:brug af regex-indeks
i dokumenterne), men dette burde stadig være meget hurtigere end at bruge $where
.
Denne løsning (duplikering af _id
streng) vil medføre noget ekstra lagerplads pr. dokument, men du kan beslutte, at de yderligere 24-30 bytes (strengnyttelast og et kort feltnavn) er ubetydelig.