Writers transform parsed objects into files and directories on disk.
Writers are implemented behind the scenes in terms of chunks as defined in firmant.chunks. This is because writers need to do work at two different points in time, with other chunks being scheduled in between. The first chunk executed by a writer will forward-declare URLs that the writer claims responsibility for. The second chunk renders objects and saves the result to disk.
Modules in this package:
| atom | |
| feeds | |
| j2 | |
| posts | |
| static | |
| staticrst |
Bases: firmant.chunks.AbstractChunk
The base class of all writers.
This class defines an abstract base class that all writers are required to adhere to. To use this class in the creation of a writer, create a subclass with all necessary methods and properties overwritten.
See also
To create a new type of writer, inherit from Writer:
>>> class SampleWriter(Writer):
... extension = 'txt'
... def key(self, obj):
... return {'obj': str(obj)}
... def obj_list(self, environment, objects):
... return objects.get('objs', [])
... def render(self, environment, path, obj):
... print 'Save object "%s" to "%s"' % (obj, path)
The new writer meets the criteria for two different abstract base classes:
>>> import firmant.chunks
>>> issubclass(SampleWriter, firmant.chunks.AbstractChunk)
True
>>> issubclass(SampleWriter, Writer)
True
Warning
When creating a writer, do not store state in the writer itself. While it appears that a writer is a single object, it will actually share state across three or more chunks during typical usage.
If it is necessary to store state, place it in environment keyed to the writer class:
>>> environment[SampleWriter] = 'stored state goes here'
This is because of the need to split actions between url forward-declaration and rendering.
The remainder of this section is devoted to describing the implementation details of Writer‘s template methods.
Chunks are passed environment and object dictionaries. While it is not technically a chunk, the Writer interface follows the same pattern. When called with an environment and set of objects, a writer will return two more chunks (in addition to the environment and object dictionaries).
>>> environment = {'log': logger
... ,'urlmapper': urlmapper
... }
>>> environment['urlmapper'].add(
... routing.SinglePathComponent('obj', str)
... )
>>> objects = {'objs': ['obj1', 'obj2', 'obj3']}
>>> sw = SampleWriter(environment, objects)
>>> sw.scheduling_order
10
>>> pprint(sw(environment, objects))
({'log': <logging.Logger instance at 0x...>,
'urlmapper': <firmant.routing.URLMapper object at 0x...>},
{'objs': ['obj1', 'obj2', 'obj3']},
[<firmant.writers.SampleWriter object at 0x...>,
<firmant.writers.SampleWriter object at 0x...>])
Note
The chunks returned do not share any state with the Writer that created them. The fact that the class name is the same is an implementation detail that may change in the future.
The first chunk is the chunk that will build the urls, while the second is used for rendering. Neither chunk returns more chunks.
>>> environment, objects, (urls, render) = sw(environment, objects)
>>> urls.scheduling_order
500
>>> render.scheduling_order
900
>>> pprint(urls(environment, objects))
({'log': <logging.Logger instance at 0x...>,
'urlmapper': <firmant.routing.URLMapper object at 0x...>,
'urls': {'firmant.writers.SampleWriter': ['http://testurl/obj1/',
'http://testurl/obj2/',
'http://testurl/obj3/']}},
{'objs': ['obj1', 'obj2', 'obj3']},
[])
>>> pprint(render(environment, objects))
Save object "obj1" to "outputdir/obj1/index.txt"
Save object "obj2" to "outputdir/obj2/index.txt"
Save object "obj3" to "outputdir/obj3/index.txt"
({'log': <logging.Logger instance at 0x...>,
'urlmapper': <firmant.routing.URLMapper object at 0x...>},
{'objs': ['obj1', 'obj2', 'obj3']},
[])
The extension that will be used when finding the path/url of an object.
This will be passed to a firmant.routing.URLMapper instance.
Map the object to a dictionary of attributes.
The attributes will be passed to the path() and :meth`url` methods of firmant.routing.URLMapper.
The objects that should be passed to render()
It will be passed the environment and objects dictionaries that were passed to the chunk.
Write the object to the path on filesystem.
path will be a path under the output directory. obj is one of the objects returned by obj_list.
The following scheduling orders apply to writers:
The string displayed when interacting with the user.
This should be the name of the class they must specify in the configuration. The default value should not be changed.