publ betaReference (MCP guide)
Open publ console

publ Reference

membership_create

Create one GENERAL membership with the original wizard's title, card styling, five optional benefit statements, optional original card images and installed-feature selection in one operation. Artwork implementation:

Prepare the choices

Call memberships_get without an existing membership:

{"channelCode":"selected-channel-code","view":{"kind":"create-options"}}

The response includes built-in cardDefaults and accessOptions. Choose installed numeric IDs whose canSelect is true and copy accessOptions.revision. This is a separate installed-feature revision, not an existing membership revision. An inactive eligible feature can be selected without being activated. Filtered features cannot be newly granted; do not copy display names or store codes into the ID array.

Compose and submit

Replace the example IDs and revision with returned values. Without image uploads, dryRun:true returns the complete planned request. With uploads, it returns the pre-upload plan described below; no grant, upload, POST, new task record or reservation is made. After reviewing the plan, send the same choices with dryRun:false or omit it. Keep the same requestId for the logical operation.

The trimmed title must contain 4–50 UTF-16 code units. Five optional statements (benefitAlpha through benefitEcho) each allow up to 50 units. Empty or omitted statements are omitted from the source POST and must read back as empty strings. Benefit text alone grants no feature access. Omitted image slots keep the source built-in background and logo; explicit uploads or default-logo removal are supported below. Omitted card styling uses A with SOLID #455EEF4D; selectable designs are A/B. Overlays are NONE, SOLID with primary, or GRADIENT with both primary and secondary; colors use six/eight-digit hex. Arbitrary image URLs remain unsupported.

access.installedPAppIds is the complete desired set. An intentionally empty set requires confirmEmpty:true. Missing, duplicate, filtered or changed choices fail before dispatch. OWNER or DELEGATEE with MANAGE_MONETIZATION is required in the exact selected channel. The original create control adds no paid-plan or active- monetization prerequisite, so the bridge does not invent one. Backend rejection still fails; it is not converted into completion.

After any requested image uploads are acknowledged, the workflow rechecks context/options, records dispatch, sends one complete POST, saves the validated receipt and independently reads its exact membership mid. Success is MEMBERSHIP_CREATED only when identity, title, all card/benefit fields and exact installed ID/code associations agree. It creates no subscription product, price, purchase, payment, feature activation or ACL change. Use membership_update for later supported edits and membership_display_apply for a separate display choice.

Create with original card artwork

The image fields belong directly inside card, not inside an existing-membership patch. They can accompany card styling, benefits and the complete access selection in the same creation request.

Input Accepted value and effect
card.backgroundImage Omit for the built-in background, use "reset-default" to select it explicitly, or {kind:"upload",file:{filename,base64}} for original PNG/JPEG/GIF up to and including 5 MiB (5242880 bytes).
card.logoImage Omit for the built-in logo, use "remove" to create with an empty logo reference, or {kind:"upload",file:{filename,base64}} for original PNG/SVG up to 1 MiB (1048576 bytes).

The background limit follows the source chooser; the logo limit is bridge transport policy. Supply a matching basename and canonical base64 without a local path, URL, data-URL prefix or whitespace. Original bytes are preserved without resizing. The shared parser checks bounded file/container structure, not complete decoding, SVG sanitization or browser rendering. The host must configure the channel-bound resource gateway, bucket and region; the caller supplies no credentials or guessed pApp consumer. Missing configuration returns UPLOAD_NOT_CONFIGURED.

This example reuses tiny illustrative PNG/SVG files to show the input shape. Replace them with the intended original artwork, and replace the installed IDs/options revision from create-options. It is a dry-run example, not evidence of an upload or a rendered membership card.

{
  "requestId": "membership-create-artwork-001",
  "channelCode": "selected-channel-code",
  "title": "Community membership",
  "access": {
    "installedPAppIds": [
      17,
      24
    ],
    "expectedOptionsRevision": "0000000000000000000000000000000000000000000000000000000000000000"
  },
  "dryRun": true,
  "card": {
    "designSchema": "B",
    "backgroundImage": {
      "kind": "upload",
      "file": {
        "filename": "example-background.png",
        "base64": "iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAYAAAAfFcSJAAAADUlEQVR4nGNwjXv/HwAFEAKS9fMIJwAAAABJRU5ErkJggg=="
      }
    },
    "logoImage": {
      "kind": "upload",
      "file": {
        "filename": "example-logo.svg",
        "base64": "PHN2ZyB4bWxucz0iaHR0cDovL3d3dy53My5vcmcvMjAwMC9zdmciIHdpZHRoPSIxIiBoZWlnaHQ9IjEiPjxyZWN0IHdpZHRoPSIxIiBoZWlnaHQ9IjEiIGZpbGw9IiM0NTVFRUYiLz48L3N2Zz4="
      }
    }
  },
  "benefits": {
    "benefitAlpha": "Member news"
  }
}

To create with the built-in background and no default logo, use this separate request instead of an upload object for those slots:

{
  "requestId": "membership-create-no-logo-001",
  "channelCode": "selected-channel-code",
  "title": "Community membership",
  "access": {
    "installedPAppIds": [
      17,
      24
    ],
    "expectedOptionsRevision": "0000000000000000000000000000000000000000000000000000000000000000"
  },
  "dryRun": true,
  "card": {
    "backgroundImage": "reset-default",
    "logoImage": "remove"
  }
}

Removal clears the new card's logo reference; it does not delete a file. Explicit reset-default uses the same built-in background as omission. Neither action adds a follow-up membership update: the intended values belong to the original single creation POST.

Recovery and destination

Use task_status/task_resume with taskType:"membership-create" and the returned taskId. Status reads the journal. Status/resume never issue image grants, upload or POST, including prepared tasks with already uploaded files. A prepared task can report MEMBERSHIP_CREATE_NOT_DISPATCHED; only the identical original create input, including original image bytes, can continue unattempted effects after rechecking. Acknowledged uploads are retained; uncertain grant-sent/upload-sent stages are never replayed. A sent task with no validated receipt ID returns MEMBERSHIP_CREATE_ID_UNRESOLVED. Preserve it and inspect the console; never guess by title or retry with a different requestId. There is no automatic membership deletion or rollback. A known receipt permits only that record's fresh read and comparison; matching recovery returns MEMBERSHIP_CREATE_RECONCILED. Completed replay is historical.

The single canonical console link opens the creation form for a plan, the created membership editor after verified completion, or the membership list when no verified created identity is available. It uses the centrally configured console origin. Demo has no real console destination. Sequential checks do not provide atomic compare-and-swap, causal ownership, rendered appearance or visitor-access proof.

Inputs

Field Required here Contract
title Yes string; min length 4; max length 50
card No object
card.designSchema No A, B
card.overlay No one of: NONE, SOLID, GRADIENT (by type)
card.overlay.primary Yes When card.overlay.type is SOLID: string; pattern ^#[0-9a-fA-F]{6}(?:[0-9a-fA-F]{2})?$
card.overlay.primary Yes When card.overlay.type is GRADIENT: string; pattern ^#[0-9a-fA-F]{6}(?:[0-9a-fA-F]{2})?$
card.overlay.secondary Yes When card.overlay.type is GRADIENT: string; pattern ^#[0-9a-fA-F]{6}(?:[0-9a-fA-F]{2})?$
card.backgroundImage No reset-default or one of: local-file, more-parts, complete, cancel (by kind)
card.backgroundImage.filename Yes When card.backgroundImage.kind is local-file: string; min length 1; max length 240; pattern ^[^/\\:\x00-\x1f\x7f]+$; The name of the file on this computer, with its extension.
card.backgroundImage.byteLength Yes When card.backgroundImage.kind is local-file: integer; greater than 0; The exact file size in bytes (for example from wc -c < FILE or stat).
card.backgroundImage.sha256 No When card.backgroundImage.kind is local-file: string; pattern ^[0-9a-f]{64}$
card.backgroundImage.uploadId Yes When card.backgroundImage.kind is more-parts: string; pattern ^upl_[A-Za-z0-9_-]{22}$
card.backgroundImage.fromPart Yes When card.backgroundImage.kind is more-parts: integer; minimum 1; maximum 10000
card.backgroundImage.uploadId Yes When card.backgroundImage.kind is complete: string; pattern ^upl_[A-Za-z0-9_-]{22}$
card.backgroundImage.parts Yes When card.backgroundImage.kind is complete: array; min items 1; max items 10000
card.backgroundImage.parts[].partNumber Yes When card.backgroundImage.kind is complete: integer; minimum 1; maximum 10000
card.backgroundImage.parts[].etag Yes When card.backgroundImage.kind is complete: string; min length 1; max length 200
card.backgroundImage.measured No When card.backgroundImage.kind is complete: object; What the video measures on this computer, read with measureCommand.
card.backgroundImage.measured.durationSeconds Yes When card.backgroundImage.kind is complete: number; maximum 1000000; greater than 0; Video duration in seconds (ffprobe format.duration).
card.backgroundImage.measured.frameRate Yes When card.backgroundImage.kind is complete: number; maximum 1000; greater than 0; Frames per second (ffprobe avg_frame_rate, for example 30000/1001 = 29.97).
card.backgroundImage.measured.width Yes When card.backgroundImage.kind is complete: integer; maximum 100000; greater than 0
card.backgroundImage.measured.height Yes When card.backgroundImage.kind is complete: integer; maximum 100000; greater than 0
card.backgroundImage.measured.frameRateMode No When card.backgroundImage.kind is complete: CFR, VFR
card.backgroundImage.measured.minFrameRate No When card.backgroundImage.kind is complete: number; maximum 1000; greater than 0
card.backgroundImage.measured.maxFrameRate No When card.backgroundImage.kind is complete: number; maximum 1000; greater than 0
card.backgroundImage.uploadId Yes When card.backgroundImage.kind is cancel: string; pattern ^upl_[A-Za-z0-9_-]{22}$
card.logoImage No remove or one of: local-file, more-parts, complete, cancel (by kind)
card.logoImage.filename Yes When card.logoImage.kind is local-file: string; min length 1; max length 240; pattern ^[^/\\:\x00-\x1f\x7f]+$; The name of the file on this computer, with its extension.
card.logoImage.byteLength Yes When card.logoImage.kind is local-file: integer; greater than 0; The exact file size in bytes (for example from wc -c < FILE or stat).
card.logoImage.sha256 No When card.logoImage.kind is local-file: string; pattern ^[0-9a-f]{64}$
card.logoImage.uploadId Yes When card.logoImage.kind is more-parts: string; pattern ^upl_[A-Za-z0-9_-]{22}$
card.logoImage.fromPart Yes When card.logoImage.kind is more-parts: integer; minimum 1; maximum 10000
card.logoImage.uploadId Yes When card.logoImage.kind is complete: string; pattern ^upl_[A-Za-z0-9_-]{22}$
card.logoImage.parts Yes When card.logoImage.kind is complete: array; min items 1; max items 10000
card.logoImage.parts[].partNumber Yes When card.logoImage.kind is complete: integer; minimum 1; maximum 10000
card.logoImage.parts[].etag Yes When card.logoImage.kind is complete: string; min length 1; max length 200
card.logoImage.measured No When card.logoImage.kind is complete: object; What the video measures on this computer, read with measureCommand.
card.logoImage.measured.durationSeconds Yes When card.logoImage.kind is complete: number; maximum 1000000; greater than 0; Video duration in seconds (ffprobe format.duration).
card.logoImage.measured.frameRate Yes When card.logoImage.kind is complete: number; maximum 1000; greater than 0; Frames per second (ffprobe avg_frame_rate, for example 30000/1001 = 29.97).
card.logoImage.measured.width Yes When card.logoImage.kind is complete: integer; maximum 100000; greater than 0
card.logoImage.measured.height Yes When card.logoImage.kind is complete: integer; maximum 100000; greater than 0
card.logoImage.measured.frameRateMode No When card.logoImage.kind is complete: CFR, VFR
card.logoImage.measured.minFrameRate No When card.logoImage.kind is complete: number; maximum 1000; greater than 0
card.logoImage.measured.maxFrameRate No When card.logoImage.kind is complete: number; maximum 1000; greater than 0
card.logoImage.uploadId Yes When card.logoImage.kind is cancel: string; pattern ^upl_[A-Za-z0-9_-]{22}$
benefits No object
benefits.benefitAlpha No string; max length 50
benefits.benefitBravo No string; max length 50
benefits.benefitCharlie No string; max length 50
benefits.benefitDelta No string; max length 50
benefits.benefitEcho No string; max length 50
access Yes object; The complete intended installed-feature set and current options revision from memberships_get view.kind create-options. Empty requires confirmEmpty:true.
access.installedPAppIds Yes array; items: integer; greater than 0; max items 10000; The complete desired installed-feature ID set, not additions only. Omit access to preserve all associations. Copy IDs from memberships_get detail with includeAccessOptions:true.
access.confirmEmpty No true
confirmToken No string; pattern ^ct[a-f\d]{32}$; The confirmToken from this tool's preview result. Omit it to preview; repeat the same input with it to execute.