npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

storyblok-backup

v0.5.0

Published

npx CLI tool to create a full backup of a Storyblok space and restore single resources from it.

Downloads

1,391

Readme

Storyblok Backup CLI

npm version license

A npx CLI tool to create a full backup of a space of the Storyblok CMS.

A restore tool to restore (create or update) resources is also included.

The backup script will fetch the following resources of a Storyblok space using the Management API and archive them in a zip file:

  • Stories
  • Collaborators
  • Components
  • Component groups
  • Assets (optionally incl. original files)
  • Asset folders
  • Internal Tags
  • Datasources (incl. entries)
  • Space
  • Space Roles
  • Tasks
  • Activities
  • Presets
  • Field types
  • Webhooks
  • Workflows
  • Workflow stages
  • Workflow stage changes
  • Releases
  • Pipeline Branches
  • Access Tokens

The restore script is able to individually restore the resources from the backup files (via update or create) with the following exceptions:

  • Assets: Only updating asset-resource-data is supported. Creating assets and updating asset-files is not supported.
  • Field types: Currently not supported
  • Workflow stage changes: No update possible.
  • Access Tokens: Creating access tokens from backup makes no sense, since it will result in a new token-string.

Table of contents

Installation


# simply auto-download and run via npx (backup only)
$ npx storyblok-backup

# or install globally
$ npm install -g storyblok-backup

# or install for project using npm
$ npm install storyblok-backup

# or install for project using yarn
$ yarn add storyblok-backup

# or install for project using pnpm
$ pnpm add storyblok-backup

Usage

Backup

Call npx storyblok-backup with the following options:

Backup options

--token <token>       (required) Personal OAuth access token created
                      in the account settings of a Stoyblok user.
                      (NOT the Access Token of a Space!)
                      Alternatively, you can set the STORYBLOK_OAUTH_TOKEN environment variable.
--space <space_id>    (required) ID of the space to backup
                      Alternatively, you can set the STORYBLOK_SPACE_ID environment variable.
--region <region>     Region of the space. Possible values are:
                      - 'eu' (default): EU
                      - 'us': US
                      - 'ap': Australia
                      - 'ca': Canada
                      - 'cn': China
                      Alternatively, you can set the STORYBLOK_REGION environment variable.
--types <types>       Comma separated list of resource-types to backup (default=all).
                      Possible values are:
                      - 'stories'
                      - 'collaborators'
                      - 'components'
                      - 'component-groups'
                      - 'assets'
                      - 'asset-folders'
                      - 'internal-tags'
                      - 'datasources'
                      - 'space'
                      - 'space-roles'
                      - 'tasks'
                      - 'activities'
                      - 'presets'
                      - 'field-types'
                      - 'webhooks'
                      - 'workflow-stages'
                      - 'workflow-stage-changes'
                      - 'workflows'
                      - 'releases'
                      - 'pipeline-branches'
                      - 'access-tokens'
--omit-types <types>  Comma separated list of resource-types to omit.
--with-asset-files    Downloads all files (assets) of the space (default=false).
--output-dir <dir>    Directory to write the backup to (default=./.output)
                      (ATTENTION: Will fail if the directory already exists!)
--force               Force deletion and recreation of existing output directory.
--create-zip          Create a zip file of the backup (default=false).
--zip-prefix <dir>    Prefix for the zip file. (default='backup').
                      (The suffix will automatically be the current date.)
--verbose             Will show detailed output for every file written.
--help                Show this help

OAuth token, space-id and region can be set via environment variables. You can also use a .env file in your project root for this (see .env.example).

Minimal backup example

npx storyblok-backup --token 1234567890abcdef --space 12345

This will create the folder ./.output/backup and fetch all resources sorted into folders.

Maximal backup example

npx storyblok-backup \
    --token 1234567890abcdef \
    --space 12345 \
    --region ap \
    --types "stories,components" \
    --with-asset-files \
    --output-dir ./my-dir \
    --force \
    --create-zip \
    --zip-prefix daily \
    --verbose

This will create the folder ./my-dir/backup, fetch all resources (incl. the original file assets) sorted into folders, zip them to ./my-dir/daily-Y-m-d-H-i-s.zip, and log every written file to console.

Continuous backup integration examples

You can use this script to create periodic backups of Storyblok spaces using GitHub Actions and artifacts, or commit each content change to a git repository usint Storyblok's webhooks.

Example for a GitHub workflow for a complete backup as an artifact

Here would be an example for a weekly backup, that removes the artifacts/backups from previous runs and uploads a new one:

name: Weekly Storyblok Backup

on:
  schedule:
    - cron: '0 0 * * 0'

jobs:
  backup:
    runs-on: ubuntu-latest
    permissions:
      actions: write

    steps:
      - name: Perform Backup
        env:
          STORYBLOK_OAUTH_TOKEN: ${{ secrets.STORYBLOK_OAUTH_TOKEN }}
          STORYBLOK_SPACE_ID: ${{ secrets.STORYBLOK_SPACE_ID }}
        run: npx storyblok-backup

      - name: Delete Old Artifacts
        uses: actions/github-script@v6
        id: artifact
        with:
          script: |
            const res = await github.rest.actions.listArtifactsForRepo({
                owner: context.repo.owner,
                repo: context.repo.repo,
            })

            res.data.artifacts
                .filter(({ name }) => name === 'weekly-backup')
                .forEach(({ id }) => {
                  github.rest.actions.deleteArtifact({
                      owner: context.repo.owner,
                      repo: context.repo.repo,
                      artifact_id: id,
                  })
                })

      - name: Upload Artifact
        uses: actions/upload-artifact@v3
        with:
          name: weekly-backup
          path: .output
          include-hidden-files: true
          if-no-files-found: error

Make sure, to set the secrets STORYBLOK_OAUTH_TOKEN and STORYBLOK_SPACE_ID in your repository settings.

Note that artifact manipulation requires the actions: write permission for the workflow. The workflow above has this permission set already.

If you create multiple workflows for daily, weekly and monthly backups, by changing the cron-schedule and the two occurrences of the artifact name weekly-backup, you will always have exactly one daily, weekly and monthly backup.

Also keep in mind, that there is a limit on artifact storage and runner minutes (see GitHub docs).

Example for a GitHub workflow for an incremental git-commit-based backup

The following workflow should run via webhook on every relevant change (e.g.publish) in Storyblok. It creates a new current backup (excl. asset files) and commits them to the current repository in the backup folder. This enables an incremental git-commit-based backup of all Storyblok-content.

name: Incremental Repository Backup

on:
  repository_dispatch:
    types:
      - webhook

concurrency:
  group: ${{ github.workflow }}-${{ github.ref }}
  cancel-in-progress: true

jobs:
  backup:
    runs-on: ubuntu-24.04
    permissions:
      contents: write

    steps:

      - name: Checkout
        uses: actions/checkout@v4
        with:
          ref: 'main'

      - name: Perform backup
        env:
          STORYBLOK_OAUTH_TOKEN: ${{ secrets.STORYBLOK_OAUTH_TOKEN }}
          STORYBLOK_SPACE_ID: ${{ secrets.STORYBLOK_SPACE_ID }}
        run: npx storyblok-backup

      - name: Copy files into repository
        run: |
          rm -rf backup
          cp -r .output/backup .
          rm -rf .output

      - name: Perform commit
        run: |
          git config --global user.name 'Your User'
          git config --global user.email '[email protected]'
          git add backup
          git diff --staged --quiet || git commit -m "content: update `date +'%Y-%m-%d %H:%M:%S'`"
          git push

Make sure, to set the secrets STORYBLOK_OAUTH_TOKEN and STORYBLOK_SPACE_ID in your repository settings.

Note that actions performing commits require the contents: write permission for the workflow. The workflow above has this permission set already.

A webhook to the URL https://api.github.com/repos/{owner}/{repo}/dispatches must be setup and triggered by every relevant content change in Storyblok. Since Storyblok's webhooks do not support authentication headers - which are required by GitHub - you can use Pipedream (or a similar service) as an intermediate webhook.

Restore

Make sure to install the package first (see Installation).

Call npx storyblok-restore with the following options:

Restore options

--token <token>     (required) Personal OAuth access token created
                    in the account settings of a Stoyblok user.
                    (NOT the Access Token of a Space!)
                    Alternatively, you can set the STORYBLOK_OAUTH_TOKEN environment variable.
--space <space_id>  (required) ID of the space to backup
                    Alternatively, you can set the STORYBLOK_SPACE_ID environment variable.
--region <region>   Region of the space. Possible values are:
                    - 'eu' (default): EU
                    - 'us': US
                    - 'ap': Australia
                    - 'ca': Canada
                    - 'cn': China
                    Alternatively, you can set the STORYBLOK_REGION environment variable.
--type <type>       (required) Type of resource to restore. Possible values are:
                    - 'story'
                    - 'collaborator'
                    - 'component'
                    - 'component-group'
                    - 'asset'
                    - 'asset-folder'
                    - 'internal-tag'
                    - 'datasource'
                    - 'datasource-entries'
                    - 'space'
                    - 'space-role'
                    - 'task'
                    - 'preset'
                    - 'webhook'
                    - 'workflow'
                    - 'workflow-stage'
                    - 'release'
                    - 'pipeline-branch'
                    - 'access-token'
--file <file>       (required) File of resource to restore.
--publish           Perform a publish after restore of a story (default=false).
--create            Create a new resource instead of updating (default=false).
                    Not supported for assets.
--propagate         Propagate new story UUID to referencing stories (default=false).
                    Usable with create and stories. A create results in a new ID and UUID.
                    This option will update all stories referencing the old
                    UUID (as stated in the backup-json) with the new one.
--id <file>         (required if type=datasource-entries and create is set)
                    ID of datasource the entries belong to.
--verbose           Will show detailed result of the restore process.
--help              Show this help

Minimal restore example

npx storyblok-restore --token 1234567890abcdef --space 12345 --type story --file ./.output/backup/123456789.json

This will restore the story from the stated file by updating it.

Maximal restore example

npx storyblok-restore \
  --token 1234567890abcdef \
  --space 12345 \
  --region ap \
  --type story \
  --file ./.output/backup/123456789.json \
  --publish \
  --create \
  --propagate \
  --verbose

This will restore the story by creating a new story, immediately publish it, and log the API result to console.

License

This package is open-sourced software licensed under the MIT license.