Skip to content

tilttek/badges

✅ published

Badges your members earn by what they do and show when they choose.

tilttek/badges awards badges and achievements from the members' activity, recorded by tilttek/activity. A badge has a criterion read from the journal — a number of activities, a total of their quantities, a first time, days in a row, a period, a combination of criteria, a value the application measures, or an award by hand —, and the progress towards it is computed and shown, 7 of 10. Tiers link the badges of a series — bronze, silver, gold —; a repeatable badge is earned again each time its target is reached again; a revocable badge is withdrawn when the activity that earned it is cancelled; a hidden achievement is shown, and its criterion with it, only once earned. When a rule changes, the badges are recomputed from the journal over the period the application chooses.

A badge earned is private until the member shows it. The member chooses a title worn beside their name, the showcase of their profile and its order, what they share and where, and which other applications may read their badges, a consent they withdraw at any time. Erasing a member removes their awards, the contributions of their activity, their profile and their consents. tilttek/badges-bundle issues a badge as an Open Badges 3.0 credential, at the member's request, through phil/open-badges.

It is for an application that recognises what its members do — a community site, a game site, a store — and wants badges it can recompute and members who decide what is public. tilttek/badges-bundle integrates it with Symfony and keeps the badges in Doctrine DBAL; an application without Symfony takes the library alone, with its stores in memory or its own.

It is a plain PHP library whose dependencies are tilttek/activity, the journal the criteria read, phil/resource, the opaque reference of a member, psr/clock, and the mbstring extension. Members are references the application gives, member:44: the library never reads a name, an e-mail or an account.

The design is small: a Badge with its Criterion, held by a Catalog; BadgeProjection reads the journal into Contributions and Awards through four stores; Evaluator computes a Progress; Badges serves the application — awards, progress, Profile, Showcase, sharing, consents, erasure.

Status

PartState
Badge, Tier, Catalog: codes, texts, images, tiers, repeatable, hidden and revocable badges, a catalog from plain valuesImplemented and tested
Criteria: Count (and first times), Total, Streak, Measure, Manual, AtLeast (all or some), periods and context conditions in Scope, CriterionReaderImplemented and tested
BadgeProjection and Evaluator: contributions once per activity, awards and repeats, withdrawals, rebuilds without announcing againImplemented and tested
Badges: awards, progress, overview, manual awards, profile, showcase, title, sharing, consents of other applications, erasureImplemented and tested
Stores — ProgressStore, AwardStore, ProfileStore, GrantStore — and their implementations in memoryImplemented and tested
Exceptions under one BadgesException interfaceImplemented and tested

Documentation

DocumentWhat it covers
InstallationRequirements and installing.
Badges and criteriaBadges, tiers, every kind of criterion, periods, context conditions, the catalog from plain values.
AwardingThe projection, progress, repeatable and revocable badges, manual awards, rebuilds, observers.
What a member showsPrivate badges, the showcase, the title, sharing, the consent of other applications.
ErasureWhat erasing a member removes.
Writing a storeThe contracts of the four stores an application's storage implements.
Extension pointsWhat an application gives the library: stores, measures, criteria, observers, sharing, the clock.
ExceptionsBadgesException and its exceptions, with their messages.
TestingThe library's tests and mutation bar, and how to test code that awards badges.
ReferenceEvery type of the library, with its role.

Quick start

composer require tilttek/badges
use Tilttek\Badges\BadgeProjection;
use Tilttek\Badges\Badges;
use Tilttek\Badges\Catalog;
use Tilttek\Badges\Evaluator;
use Tilttek\Badges\Store\InMemoryAwardStore;
use Tilttek\Badges\Store\InMemoryGrantStore;
use Tilttek\Badges\Store\InMemoryProfileStore;
use Tilttek\Badges\Store\InMemoryProgressStore;

$catalog = Catalog::fromArray([
    'commenter' => ['name' => 'Commenter', 'criterion' => ['count' => ['verbs' => ['news.commented'], 'times' => 10]]],
    'regular' => ['name' => 'Regular', 'criterion' => ['streak' => ['verbs' => ['site.visited'], 'days' => 7]]],
], 'America/Toronto');
$progress = new InMemoryProgressStore();
$awards = new InMemoryAwardStore();
$evaluator = new Evaluator($catalog, $progress);

$projection = new BadgeProjection($evaluator, $progress, $awards); // handed to tilttek/activity's projections
$badges = new Badges($evaluator, $progress, $awards, new InMemoryProfileStore(), new InMemoryGrantStore(), $clock);

$badges->progress($member, 'commenter'); // 7 of 10

Requirements

PHP 8.5 or later, with the mbstring extension.

Contributing

Contributions are welcome on the PHIL monorepo: read the contribution guide and the code of conduct. Report a vulnerability privately, as the security policy explains, never in a public issue.

License

MIT, © Philippe Gamache, doing business as Le Gnome Archiviste; a Tilttek project. See LICENSE.