piano_c1x 1.0.8
piano_c1x: ^1.0.8 copied to clipboard
Piano C1X SDK for Flutter.
Piano C1X SDK for Flutter #
Joins Piano Composer and Piano Cxense: every experience the integration is enabled for is reported to Cxense as a page view carrying the state of the Composer user, and Composer receives the Cxense user as its browser id — so the segments of a user reach the experiences of that same user, without your application wiring the two SDKs together itself.
Installation #
Add the dependencies to your pubspec.yaml:
dependencies:
piano_common: ^1.0.8
piano_composer: ^1.0.8
piano_cxense: ^1.0.8
piano_c1x: ^1.0.8
Supported Platforms #
The platforms piano_cxense supports, since the page views this integration
reports are queued in its database: Android, iOS and macOS out of the box, and
Windows and Linux when your application installs a
sqflite_common_ffi factory
before Piano.init. See piano_cxense.
Getting Started #
C1X is a module of the Piano SDK: pass a PianoC1xConfiguration to Piano.init
next to the PianoCxenseConfiguration the page views are queued through, and
reach the integration through piano.c1x. Composer needs no configuration of its
own — the integration enables itself for the instance.
import 'package:piano_c1x/piano_c1x.dart';
import 'package:piano_common/piano_common.dart';
import 'package:piano_composer/piano_composer.dart';
import 'package:piano_cxense/piano_cxense.dart';
final piano = await Piano.init(
endpoint: PianoEndpoint.production,
aid: '<AID>',
configurations: [
PianoCxenseConfiguration(
// Recommended for C1X: a page view reported for an experience stays open
// for merging with the next one for half a minute.
eventsMergePeriod: const Duration(seconds: 30),
),
const PianoC1xConfiguration(),
],
);
// Enabled once, for every Composer client of the instance.
piano.c1x.enable(siteId: '<CXENSE_SITE_ID>');
final response = await piano.composer().execute(
PianoComposerRequest(url: 'https://piano.io/article'),
);
Reaching piano.c1x without PianoC1xConfiguration — or after
piano.close() — throws a StateError. The integration is off until enable
is called, so the order the configurations are passed in does not matter.
The page views are queued through the Cxense module of the same instance, so
enable throws a StateError when the instance was created without a
PianoCxenseConfiguration.
Enabling #
piano.c1x.enable(
// The Cxense site id of the application.
siteId: '<CXENSE_SITE_ID>',
);
Call it once, after Piano.init: the integration enables itself for the instance
rather than for one client, so every client piano.composer() hands out reports
its experiences from there on — the clients created before enable as well as the
ones created after it. Calling it again re-enables the integration for the passed
site.
The Composer requests of the instance have to carry a contentId or a url that
is a valid http/https address while the integration is enabled, because a
Cxense page view is identified by one of them: a request that carries neither is
refused by PianoComposerClient.execute with an ArgumentError before it is
sent, rather than after the experience was executed successfully.
Re-enabling applies to the requests that are sent from there on. An experience that is already on its way is reported for the settings it was executed with.
isEnabled, siteId and userId report what the integration is doing at the
moment; the last two are null while it is disabled.
The Reported User #
The Cxense user (ckp) the page views are reported for — and which Composer
receives as its browser id — is the user of the integration:
piano.c1x.enable(siteId: '<CXENSE_SITE_ID>', userId: '<CXENSE_USER_ID>');
It belongs to the integration alone. The events the application tracks itself
through piano.cxense keep reporting the user of that module, so the two can be
told apart: what joins the page view of an experience to the Piano user is the
external user id it carries — cxenseCustomerPrefix and the Composer user —
rather than the ckp.
The user is read for every Composer request rather than captured, so signing a
reader in is enable with the new user and applies from the next request on:
// The same site, so the integration keeps the generation it runs on.
piano.c1x.enable(siteId: '<CXENSE_SITE_ID>', userId: '<SIGNED_IN_USER_ID>');
An experience that is already on its way keeps the user it was executed for, so the page view of the article a reader was looking at before signing in is not attributed to the user who signed in halfway through it.
That user is taken for the request object the experience is executed for, so two
executions of one object share the user taken last. Dart hands out a const
request as a single instance, however many places it is written in, which is what
makes this worth knowing:
const request = PianoComposerRequest(url: 'https://piano.io/article');
// One object executed twice at once: both page views report the user that was
// taken for the second execution.
await Future.wait([
piano.composer().execute(request),
piano.composer().execute(request),
]);
Build a request per execution to keep the two apart. Only overlapping executions share a user — executing one object again after its page view was reported is fine.
Omitting userId asks for no change: the integration keeps the user it was last
given, across disable as well. An integration that was never given one reports
for piano.cxense.userId instead, which
starts out as the device id of the instance — so an application that has a single
Cxense user for everything it reports names it once, on the Cxense module, and
leaves enable a site alone.
Disabling #
piano.c1x.disable();
The Composer clients of the instance keep working: they stop reporting page views
to Cxense and stop sending the Cxense user as their browser id — a client that
carries a browserIdProvider of its own keeps reporting that one, and an
interceptor your application enabled itself is left alone. Disabling twice does
nothing twice, and piano.close() disables the integration together with the rest
of the instance.
Unlike re-enabling, this applies to the experiences that are already on their way:
an experience that is executed while disable is called reports no page view.
What Is Reported #
Every experience a Composer client of the instance executes is reported as a
PianoCxensePageViewEvent, queued through piano.cxense and sent by its
dispatch loop:
userId(ckp) is the user the experience was executed for, andsiteIdthe site the integration was enabled for;location,contentIdandreferrerare theurl,contentIdandrefererof the Composer request;- the
userStatecustom parameter is the state of the Composer user:anonfor a user Composer knows no id of,registeredfor one it knows an id of but no access for, andhasActiveAccessfor one with at least one access; - the external user id is the Composer user id under your Cxense customer prefix, which the experience response carries — this is what joins the Composer user and the Cxense user;
rndis the page view id Composer reported the experience under, so the experience and the page view reported for it carry the same one.
Do not track a page view of your own for a screen that executes an experience, since this is what reports it — a second page view of the same page would count that page twice.
Nothing here fails an experience that was executed successfully: whatever cannot
be reported is logged through the logger of the Piano instance instead. The
cases that report no page view at all are:
- the response carries no Cxense customer prefix, which means C1X is not configured for your application — ask Piano support to turn it on;
- the response holds no
ExperienceExecuteevent to read the state of the user from; - the page view cannot be built, or cannot be queued in the Cxense database.
The cases that report the page view without a part of it are:
- a
refererCxense would refuse is dropped, since it is metadata of the page view rather than what identifies it; - a Composer user id or customer prefix Cxense would refuse leaves the page view without its external user id, so the page view is still counted even though it is not joined with the Composer user.
Set eventsMergePeriod on the Cxense configuration to let a page view stay open
for the events that follow it. Note that a merged event joins the queued page view
under that one's rnd: a second experience executed for the same URL within the
period is merged into the first record instead of being reported under its own
page view id.
Merging stops at the Composer user, though. An experience executed for another
user — after a login, say, which is what makes the same URL worth executing again —
is reported as a page view of its own, so a record never joins the rnd of one
user with the identity of another.
Recommendations #
The recommendations of the Cxense Content API are not part of this package:
query them with piano.cxense.content and display them with the widgets of
piano_templates.
Several Instances #
An application that reports to more than one Piano account runs one Piano
instance per account, and the integration belongs to the instance it was
configured on: piano.c1x reports the page views of that instance through the
Cxense module of that same instance, so enabling or disabling one instance
leaves the other one alone.