Attribution¶
MCL Theme includes support for giving attribution to authors of the
articles via mcl-attribution directive, which will display their
names with links to their accounts and profile pictures (up to two
people at at a time, with rest hidden behind “et al.” abbreviation).
You can see an example of attribution block on the top right corner of this very page.
Directive¶
- .. mcl-attribution::¶
The
mcl-attributioncan be used to manually add an attribution block to the top of the page.- :authors:¶
Name of authors, separated by semicolons (
;).
- :authors-pfps:¶
Links to authors’ icons/profile pictures, separated by semicolons (
;). Profile pictures are only displayed for the first two authors: first author’s PFP is bigger, and second author’s PFP is going to be smaller, tucked beneath first one’s PFP, fully revealed on hover.
- :authors-links:¶
Links to authors’ pages (usually their GitHub or Codeberg profile), separated by semicolons (
;).
- :last-modified:¶
Small block of text to be put below authors’ names. It is intended to specify the date of last time a page was edited.
Note
You can’t have multiple attribute blocks on an article, but you can have multiple directives in source. Parser scans the document top to bottom, so last directive will be used to create the block.
Automatic attribution functionality always inserts it’s
directives at “line zero” of the document, so having an
mcl-attribution in document will override attribution block
that was auto-generated.
Tip
mcl-attribution directive can be placed anywhere in the
document source, but it is prefered to put it at the very top
of the file, before or immediately after the first-level
heading.
Regardless of where mcl-attribution is placed in the document,
it will override attribution block that was auto-generated.
Example¶
To generate attribution block similar to one on this article, you may use the following code:
1:::{mcl-attribution}
2:authors: Wikipe-tan;Commons-tan;Wikiquote-tan
3:authors-pfps: ../_static/wikipe-tan.png;../_static/commons-tan.png
4:authors-links: https://en.wikipedia.org/wiki/Wikipedia:Wikipe-tan;https://en.wikipedia.org/wiki/Wikipedia:Wikipe-tan#Commons-tan
5:last-modified: 4 Jun 1983
6:::
Auto-Attribution¶
Most of the time, you will be working on your documentation together with other people using certain VCS (usually Git) and some SaaS Git hosting or your own GitLab/Gitea/Forgejo or even BitBucket instance.
In that case, you will probably already have some information on who has contributed the most to each document available on the git hosting’s source view page.
To avoid repeating yourself and inserting directives over and over and maintaining them, MCL Theme comes with a handy feature of Auto-Attribution, that allows you to pull attribution data from the VCS into Sphinx and generate attribution blocks, so you don’t have to.
This theme was created to be used in Mineclonia Wiki, which, as many Mineclonia-related projects do, uses Codeberg for hosting. Codeberg runs Forgejo, which is a fork of Gitea, so we have added support for Git+Gitea as attribution sources.
We do plan to add more (namely Github and SorceHut) backends in the future, but if you’re missing something, well, we will always appreciate a good pull request.
Setting up Auto-Attribution¶
Auto-Attribution is enabled by default, but the settings do require some configuration.
Generally, to enable or disable Auto-Attribution you’ll need
to set the mcl_extras_use_auto_attrib variable in your
conf.py to True or False:
mcl_extras_use_auto_attrib = True
Including and excluding documents¶
By default, Auto-Attribution will process all documents in your project, as the default value of variables that control this behaviour is this:
mcl_extras_auto_attrib_include = [ re.compile(r".*") ]
mcl_extras_auto_attrib_exclude = []
To check if a document should be auto-attributed, the
feature will see if it matches anything in the
mcl_extras_auto_attrib_include and doesn’t match
anything in mcl_extras_auto_attrib_exclude.
Those variables are of type Iterable[str | re.Pattern],
string values are matched with the == operator, and
regular expression patterns are matched with re module.
You may combine strings and patterns however you wish. The common way to use Auto-Attribution is to include everything, except index pages, like it’s done in this documentation:
mcl_extras_auto_attrib_exclude = [ re.compile(r'(?:^|.+/)index$') ]
Setting up contribution backend¶
The contribution backend is used to determine who contributed the most to each specific document and, thus, deserves attribution.
So far, we have only implemented one contribution
backend: Git. It uses git blame to scan file for
contribution info. Contributors are ranked by the
amount of lines that are associated with their
commits.
Contributors are considered to be the same if their email matches exactly. It is also assumed that they don’t use different names for their commits, otherwise inconsistencies may happen.
This backend is activated by default, so you don’t
have to pick it, but you might want to point it to
your .git directory if your source folder is not
repo’s root:
mcl_extras_auto_attrib_backend = 'git' # Optional
mcl_extras_auto_attrib_backend_options = { 'git_dir': "../.git" } # Relative to source folder (conf.py location)
Hint
If file does not belong to any commits (is Untracked), it will be assumed it has no contributors.
To fix that, commit the file and then the attribution will appear.
Setting up profile backend¶
Since Git does not store links and icons of users’ profiles, an additional backend is required to match identities of contributors to their PFPs and profile links.
We have so far only implemented the Gitea backend, which should work for Forgejo and, by extension, Codeberg and NotABug as well.
To activate it, enable it using the
mcl_extras_auto_attrib_pfp_backend configuration
variable like so:
mcl_extras_auto_attrib_pfp_backend = 'gitea'
And then configure it:
mcl_extras_auto_attrib_pfp_backend_options = {
'node': "https://codeberg.org/api",
'repo': "madoka-kaname/magical-react-ui",
'token': os.getenv("CODEBERG_KEY")
}
Names of options should be self-descriptive, but
it is worth noting that token is mandatory even
for public repositories.
Error
Since Gitea and Forgejo both lack the ability to fetch blame of the file and resolve user’s profile by their email (unless user has enabled pseudonymous emails in their settings), there is no reliable way to match contributors with their profiles.
To work around that, this backend consumes user’s profile name through their commits in repository.
As such, if user only has commits that are available locally, but not on Gitea instance, this backend will be unable to fetch their information.
When that happens, user’s PFP will be black and link won’t point anywhere. This will be remedied once the commit will be pushed to Gitea, which is where your CI should get your repo from anyways.
Inner workings¶
The Auto-Attribution feature uses two “backends”, one is for fetching contributor’s names and emails from source file, and the other is for matching those emails with profile pictures and profile links.
To do that, it uses the following classes:
1
2@dataclass
3class Contributor:
4 name: str
5 email: str
6 sample_commit: str
7 lines_contributed: int
8
9
10class ContributionBackend(ABC):
11 @abstractmethod
12 def __init__(self, env: BuildEnvironment, options: dict):
13 pass
14
15 @abstractmethod
1
2@dataclass
3class ProfilePicture:
4 picture: str
5 link: str
6
7
8class ProfilePictureBackend(ABC):
9 @abstractmethod
10 def __init__(self, env: BuildEnvironment, options: dict):
11 pass
12
13 @abstractmethod

