== Extension Point : ''IRepositoryChangeListener'' == ||'''Interface'''||''IRepositoryChangeListener''||'''Since'''||[wiki:TracDev/ApiChanges/0.12#IRepositoryChangeListener 0.12]|| ||'''Module'''||''trac.versioncontrol.api''||'''Source'''||[source:trunk/trac/versioncontrol/api.py#/IRepositoryChangeListener api.py]|| The ''IRepositoryChangeListener'' allows components to listen for and to react to changes in repositories. == Purpose == Trac can be connected to Version Control systems to e.g. [TracBrowser browse files], [TracChangeset visualize changesets] or [TracRevisionLog revision logs]. Plugins can hook into the version control module to trigger their own actions when changesets are added or modified. The main purpose for this interface is to allow plugins to react to commits and trigger appropriate actions elsewhere (e.g. sending notifications or triggering changes via commands in the commit log messages etc.) For example the CommitTicketUpdater allows referencing or closing tickets by embedding the ticket number in a commit log message. == Usage == Implementing the interface follows the standard guidelines found in [wiki:TracDev/ComponentArchitecture] and of course [wiki:TracDev/PluginDevelopment]. The method `changeset_added` is called once for each new changeset committed to the repository. For repositories that allow revision property changes (SVN), the method `changeset_modified` is called once for each changeset modified. Note that the methods will not be called if the TracRepositoryAdmin is not configured correctly to call `trac-admin $ENV changeset added/modified` from the source control hooks. == Examples == Similarly to the CommitTicketUpdater mentioned above, you might want [ticket:9263 to close a milestone from a commit log message], e.g. when committing a tag or merging a branch. The following minimal example IRepositoryChangeListener implementation could implement such a feature: {{{#!python from datetime import datetime import re from trac.core import Component, implements from trac.ticket.model import Milestone from trac.util.datefmt import utc from trac.versioncontrol.api import IRepositoryChangeListener class CommitMilestoneCloser(Component): implements(IRepositoryChangeListener) def changeset_added(self, repos, changeset): ref = re.search('complete milestone ([^\s]+)', changeset.message) if ref: milestone = Milestone(self.env, ref.group(1)) milestone.completed = datetime.now(utc) milestone.update() def changeset_modified(self, repos, changeset, old_changeset): pass }}} == Available Implementations == * CommitTicketUpdater * th:FullTextSearchPlugin: Updates search index. * th:MultiProjectCommitTicketUpdaterPlugin: Variation of CommitTicketUpdater that requires project prefixes. * th:TracTicketChangesetsPlugin: Maintains a DB table that lists changesets referencing a ticket. * th:CodeReviewerPlugin: Maintains a DB table that maps changesets to referenced tickets for code reviewing purposes. == Additional Information and References == * [apiref:trac.versioncontrol.api.IRepositoryChangeListener-class epydoc] * [apidoc:api/trac_versioncontrol_api#trac.versioncontrol.api.IRepositoryChangeListener API Reference] * See [../trac.ticket.api.IMilestoneChangeListener trac.ticket.api.IMilestoneChangeListener], [../trac.ticket.api.ITicketChangeListener trac.ticket.api.ITicketChangeListener], [../trac.wiki.api.IWikiChangeListener trac.wiki.api.IWikiChangeListener], [../trac.attachment.IAttachmentChangeListener trac.attachment.IAttachmentChangeListener] * [TracDev/DatabaseSchema/VersionControl Version control cache database schema] * Related tickets: * Generic change listener replacement: #8834, #11148, #6543, Trac-dev:7737 * #9263: Requested an implementation of a `CommitMilestoneUpdater`. * #8732: Requested an implementation of a `CommitHoursUpdater` for time tracking. * #731: Requested an implementation of a `CommitNotificationSender`. * #12898: `ICachedRepositoryChangeListener` for cached repository changes. === API History * [wiki:TracDev/ApiChanges/0.12#IRepositoryChangeListener 0.12] introduced the interface (#7723, changeset:7961)