How to search for dictionary values
The normal collection mechanism will work for searching in dictionary values.
session read: GlorpEncyclopedia. where: [:each | each entries anySatisfy: [:eachEntry | eachEntry title like: '%Ants']].Searching for keys would be a little bit trickier. If the key wasn't mapped in the value as well, then you'd need to use field-level protocol to access it. For an unmapped key
session read: GlorpEncyclopedia where: [:each | each entries anySatisfy: [:eachEntry | ((eachEntry getTable: 'ENCYC_ENTRY_LINK') getField: 'REFERENCE_NO') = 'unique']].
How to add an index
(aTable createFieldNamed: 'foo' ...) beIndexed.
Or, for a composite index
aTable addIndexfor: (Array with: field1 with: field2)
How to build queries programatically
The essence of it is that you can do
aQuery AND: anExpressionjust fine. (Same for OR:). Building the expressions is sometimes more complicated than I might like, particularly if you have things like correlated subselects, but it does work well.
Alan has written some code examples:
"I recently coded up examples [..]. The first is a Glorp example. An internal project here is looking at using Smalltalk and Glorp and wanted an example of how to dynamically build up search criteria out of a user interface. That's something that people want to do a lot. The StoreGlorp replicator has an interface kind of like that, but it's pretty complicated, and not an easy thing to follow. So I built a relatively simple (and ugly) UI that lets you query. It also uses a Store database schema, since that's one that most VW users will have access to, fully populated with meaningful data.
The application is published as GlorpSelectionExample, in the Cincom Public Repository. Of course I found a couple of interesting bugs and limitations in writing it. e.g. the ability to do object equality expression rewriting for things that don't have direct mappings to their primary keys. So you'll want a current version of Glorp in order to be able to run some of the more complex queries.
To run it, change the #login method in SelectionExampleApp to return a valid login for a Store database you hve read access to, or else just let it run against the public Store. Then do SelectionExampleApp new open.You get a user interface that allows you to choose queries and comparison operations from drop downs. It's pretty crude, but illustrates the mechanisms. Internally, it's creating predicate objects out of each set of conditions, and then evaluating the predicates to build up a glorp query expression. The arguments to the query can either be strings that correspond to attributes of the objects, or strings that are in a special dictionary to be replaced by blocks that can be used as query clauses against that object. The substitution mechanism is also too crude for a real application, but what do you want for an example."