Jul 4
2005
ContextualService 0.1.0
Here’s another library that comes from Lafcadio: ContextualService.
The ContextualService library makes it easy to manage and set services to a single, global resource such as a database or file system. By defining a service to be a child of ContextualService::Service, you
- lock off access to instantiation, so all access have to go through the service’s get method,
- and provide a simple way to set the instance, most likely for testing.
For example, Lafcadio uses ContextualService to manage access to the ObjectStore, which controls access to a database.
class Lafcadio::ObjectStore < ContextualService::Service
def initialize
...
end
end
ObjectStore.new will raise an error. To get an instance of ObjectStore, you call ObjectStore.get_object_store. If no instance has been previously set, this will instantiate the ObjectStore and save the instance for future accesses. If a mock instance has been previously set with set_object_store, it will simply return that mock instance.
Since access to the global service is attached to the class, there’s no need to pass in a mock service as an argument to any method that needs it. This can simplify testing considerably if you’ve got highly decomposed code that needs to access a global service from many places. Also, since the Context object is hidden, clients of the service don’t have to be conscious of it.
def some_method
os = Lafcadio::ObjectStore.get_object_store
# do something with the object store here
some_other_method
end
def some_other_method
os = Lafcadio::ObjectStore.get_object_store
# do something with the object store here, too
end
class TestSomeMethod < Test::Unit::TestCase
def test1
mock_object_store = Lafcadio::MockObjectStore.new
Lafcadio::ObjectStore.set_object_store mock_object_store
some_method
# assert something happened
end
end