Hosted install profile
Hosted install profiles let an organization publish a complete SeqDesk configuration on seqdesk.com and apply it to a fresh installation in one command. The installer fetches the profile JSON from the registry, validates the access code, and writes form fields, pipeline settings, sequencing tech config, ENA credentials, telemetry, and module flags into the database during setup.
npm i -g seqdesk
seqdesk -y \
--profile <id> \
--profile-code <code>The seqdesk launcher is the supported install entry point and runs the public
installer internally. If profile resolution returns 401, the access code was
missing, empty, expired, or does not match the requested profile id.
--profile and --config are mutually exclusive — use a hosted profile or a
local infrastructure JSON file, not both.
How it works
- The installer calls
https://www.seqdesk.com/api/install-profiles/<id>/resolvewith the access code in theAuthorization: Bearer <code>header. - The server validates the code (HMAC-SHA256), decrypts any stored secrets (AES-256-GCM), injects them into the configured paths, and returns the resolved JSON.
- Standard install steps run: PostgreSQL setup, Prisma migrations, seed data.
- After the database is ready,
scripts/apply-install-profile.mjswrites the resolved profile intoSiteSettings,PipelineConfig, andOrderFormConfig. Existing rows are merged by key — fields you already have are preserved unless the profile explicitly overrides them. - Profile metadata (
id,version,appliedAt) is recorded underSiteSettings.extraSettings.installProfileso the admin UI and telemetry can report which profile is active.
The resolve endpoint is dynamic and returns cache-control: no-store. Each
install pulls the current published version.
Minimal profile
The smallest viable profile is mostly metadata plus an access code definition. Everything else falls back to defaults or stays unchanged on existing installs.
{
"id": "my-facility",
"version": "1.0.0",
"minSeqDeskVersion": "1.1.82",
"enabled": true,
"profile": {
"name": "My Facility"
},
"requiredSecrets": [
{ "id": "accessCode", "label": "Profile access code", "kind": "accessCode", "required": true }
]
}Applied to a fresh install, this records the profile metadata and leaves the runtime configuration to the installer prompts and seeded defaults. Add sections from the reference below to push more configuration through the profile.
Full profile example
{
"id": "twincore",
"version": "1.0.0",
"minSeqDeskVersion": "1.1.82",
"enabled": true,
"lastUpdated": "2026-04-30",
"profile": {
"name": "TwinCore ONT MetaXpath",
"facility": "TwinCore",
"description": "Facility-ready ONT MinION Mk1D setup."
},
"requiredSecrets": [
{ "id": "accessCode", "label": "Profile access code", "kind": "accessCode", "required": true },
{ "id": "metaxpathKey", "label": "MetaXpath package token", "path": "privatePipelines.metaxpath.key", "required": true }
],
"app": { "port": 8000 },
"site": { "dataBasePath": "/data/sequencing" },
"pipelines": {
"enabled": true,
"execution": {
"mode": "slurm",
"runDirectory": "/data/pipeline_runs",
"conda": { "enabled": true, "path": "/opt/miniconda3", "environment": "seqdesk-pipelines" },
"slurm": { "queue": "cpu", "cores": 4, "memory": "64GB", "timeLimit": 12, "options": "--qos=standard" },
"nextflowProfile": "conda",
"weblogUrl": "http://seqdesk-host:8000/api/pipelines/weblog",
"weblogSecret": "replace-with-random-secret"
},
"enable": ["fastqc", "fastq-checksum", "metaxpath"]
},
"modules": { "sequencing-tech": true, "ena-sample-fields": true },
"sequencingTech": { "mode": "restrict", "onlyDeviceIds": ["ont-minion-mk1d"] },
"forms": {
"order": { "groups": [], "fields": [] },
"study": { "groups": [], "fields": [] },
"runAssignment": { "groups": [], "fields": [] }
},
"ena": {
"username": "Webin-XXXX",
"password": "replace-with-webin-password",
"testMode": false,
"brokerAccount": false,
"centerName": "MY-CENTER"
},
"telemetry": {
"enabled": true,
"endpoint": "https://www.seqdesk.com/api/telemetry/heartbeat",
"intervalHours": 24
},
"privatePipelines": {
"metaxpath": {
"packageUrl": "https://www.seqdesk.com/api/private/metaxpath/0.1.0",
"repository": "hzi-bifo/MetaxPath",
"ref": "Nextflow"
}
}
}Field reference
Top-level metadata
id: Profile identifier used in the install command and in the registry URL.version: Profile version. Bump this when the published config changes.minSeqDeskVersion: The lowest SeqDesk release that accepts this profile.enabled: Whenfalse, the profile is hidden from the public registry and the resolver returns404.lastUpdated: ISO date for the registry listing.profile.name/profile.facility/profile.description: Display fields shown in the registry and the admin UI.
requiredSecrets
Defines the secrets the profile expects. Each entry has:
id: Stable identifier. The reserved idaccessCodeis the install code.label: Human-readable name shown in the admin UI.kind:"accessCode"for the install code,"secret"for everything else.required: Whether the admin must configure a value before the profile can resolve. Defaults totrue.path: Dot-path inside the profile JSON where the resolver writes the decrypted value. For exampleprivatePipelines.metaxpath.keyinjects the secret as that property at resolve time, so the value never sits in the published config.
The accessCode entry is mandatory if requiresAccessCode is not explicitly
set to false.
app
app.port: HTTP port SeqDesk listens on.
site
site.dataBasePath: Root directory containing raw sequencing data.
runtime.database
runtime.database.mode:"auto"keeps the installer on the normal local PostgreSQL path."manual"expects encrypteddatabaseUrlanddatabaseDirectUrlsecrets and injects them intoruntime.databaseUrlandruntime.directUrl.hostedDatabase: Admin-managed metadata for a hosted database, currentlyprovider: "neon". This is written by SeqDesk.com when an admin creates a hosted Neon database for the profile. Database credentials remain encrypted secrets and are not stored in the visible profile JSON.
pipelines
pipelines.enabled: Global toggle. Whenfalse, the rest of the section is ignored and the install runs without pipeline support.pipelines.enable: Array of pipeline IDs to switch on (for example"fastqc","fastq-checksum","metaxpath").pipelines.execution.mode:"local"or"slurm".pipelines.execution.runDirectory: Directory for pipeline output and work files.pipelines.execution.conda:{ enabled, path, environment }.pipelines.execution.slurm:{ queue, cores, memory, timeLimit, options }.pipelines.execution.nextflowProfile: Nextflow profile (conda,docker,singularity,standard).pipelines.execution.weblogUrl/pipelines.execution.weblogSecret: Endpoint and shared secret for Nextflow weblog progress events.
modules
A map of { moduleId: boolean } that enables or disables individual SeqDesk
modules (for example "sequencing-tech": true, "ena-sample-fields": true).
Omitted modules keep their current state.
sequencingTech
sequencingTech.mode:"restrict"to limit the visible catalog.sequencingTech.onlyDeviceIds: Allowed device ids when restricted.sequencingTech.config: Optional inline catalog override (stored verbatim).
forms
Pre-loads the order, study, and run-assignment form builders.
forms.order.{groups, fields}forms.study.{groups, fields}forms.runAssignment.{groups, fields}
Fields and groups are merged by id (then by name). Existing entries keep
their values unless the profile entry shares a key, in which case the profile
entry wins. Entries not referenced by the profile are left untouched. The
shape matches the JSON exported from Admin > Order Form > Import / Export
and the corresponding study and run-assignment exports.
ena
ena.username/ena.password: Webin credentials.ena.testMode: Submit to the ENA test server whentrue.ena.brokerAccount: Broker account flag.ena.centerName: Submission center name.
telemetry
telemetry.enabled: Send install heartbeats to the configured endpoint.telemetry.endpoint: Heartbeat URL (defaults tohttps://www.seqdesk.com/api/telemetry/heartbeat).telemetry.intervalHours: Reporting interval.
privatePipelines
Per-pipeline package metadata. The TwinCore profile uses this for MetaXpath:
privatePipelines.<id>.packageUrl: Tarball URL.privatePipelines.<id>.repository/privatePipelines.<id>.ref: Source repo and ref for installs that pull from Git instead of a tarball.privatePipelines.<id>.key: Bearer token for the package URL. Set this via arequiredSecretsentry with the matchingpathso the token never appears in the public profile.
Secrets and access codes
- The access code is the credential the user passes with
--profile-code. It is hashed with HMAC-SHA256 and only the hash is stored. - Other secrets are encrypted at rest with AES-256-GCM. They are decrypted
during
resolveand injected into the profile JSON at thepathdeclared inrequiredSecrets. - Profiles that have unconfigured required secrets refuse to resolve.
- Change history (config, access code, and secret updates) is recorded with actor attribution.
Discovering profiles
The public registry lists profiles where enabled: true:
curl https://www.seqdesk.com/api/install-profilesEach entry includes the profile id, capabilities, minimum SeqDesk version, and the resolve URL. To inspect a single profile (without resolving its secrets):
curl https://www.seqdesk.com/api/install-profiles/<id>To resolve manually for review (returns the full installable JSON, attachment disposition):
curl -H "Authorization: Bearer <code>" \
https://www.seqdesk.com/api/install-profiles/<id>/resolve \
-o resolved-profile.jsonCreating and managing profiles
Site administrators manage profiles from https://www.seqdesk.com/admin,
under the Install Profiles tab. From there an admin can:
- Create a new profile and set its access code.
- Configure encrypted secrets and the paths they inject into.
- Create, test, and delete one hosted Neon database per profile when
NEON_API_KEYis configured on the SeqDesk.com deployment. - Update the profile configuration and bump its version.
- Review change history.
The admin detail page also shows the pre-formatted install command for the current profile id.
Deleting a hosted Neon database disables the profile first, deletes the Neon project, and clears the encrypted database URLs. Existing SeqDesk installs using that database will stop working after deletion.
Re-running on an existing install
Running the installer with --profile against an existing host applies the
current profile version on top of the database. Form fields and groups merge
by key, pipeline execution settings are overwritten where the profile sets
them, and the installProfile metadata under SiteSettings.extraSettings is
refreshed with the new version and appliedAt timestamp.
If you want to combine a profile with extra local overrides, prefer the unattended JSON flow or apply the overrides through the admin UI after the profile resolves.
When to use this
Use a hosted profile when:
- A facility wants new nodes to come up with an approved configuration without hand-editing JSON.
- Multiple installations need to stay in sync as the config evolves.
- Pipeline tokens or sequencing tech catalogs include values that must not be checked into a public repo.
For one-off installs or local development, the unattended JSON flow is usually simpler.