Data get's deleted when strapi container restarts

@Eventyret I can confirm same as @gmenih that random data are disappearing.
I’ve got v4.8.2 installed, and now not just table relation data, but also columns from the schema are missing.

1 Like

We had the same issue happen today where the article and users table were deleted.
We’re using postgres. Seems to have happened while editing articles via the admin.

Using postgres at DO. Netlify frontend. 4.7.1

Crazy this can happen.

Exactly same problem here. I restarted strapi a boom, deleted some important data from some tables (not all of them). What I did was ) update @strapi packages to latest versions, also add a strapi-google-cloud-storage plugin. I can not track what action triggered this deletion but still is super bad, really annoying and basic behavior for CMS, not to delete data without a confirmation at least.

STRAPI VERSION
v4.10.1
It happened again.

Container restarted and some, but not all, data disappeared.

Same for me, latest content type I’ve created experienced data loss, three times in three days.

Are you using a shared database, or sqlite.

I’m facing the same problem tool.
I’m using MySQL database and PM2 as Webserver.

PM2 version 5.3.0
Strapi version 4.11.5
Node version v16.20.0

The issue is still present, I’ve commented previously with v4.8 that issue was resolved, but now it had happened in production again.
I’m using heroku, and I’ve just added a new config variable to the docker that has nothing to do with Strapi at all, and all data were removed, whole database (postgres) wiped out.

1 Like

The same here.

Postgres, docker & K8S for production.

Losing some data on each reboot ( no problème with old version 3.6.9 ).

Moreover :
-When I make a dump from K8S to my local strapi, 80% of data is losse too.
-CKEditor plugin data is always loose.

We are very affraid about that, we work for a government project…

Please, there is a fix soon or someone work on it ?

Thanks in advance

As been stated many times.
If you have this issue please do post your database.js or if you have multiple environments. config/ENV/X/database.js etc

Also check that when strapi starts it does not say sqlite. As strapi won’t just delete data but mostly it’s miss configured config.
A container does not hold any data so using a sqlite file will result in dataloss. Hence why this is most likely the reason people are experiencing the issue.

Please, there is a fix soon or someone work on it ?

Please check what I said below.

At first, thanks for helping us.

My .env file i have the follow values:

DATABASE_CLIENT=mysql
DATABASE_HOST=my.custom.host
DATABASE_PORT=3306
DATABASE_NAME=database_name
DATABASE_USERNAME=database_username
DATABASE_PASSWORD=database_password

And here is my config/database.js file

const path = require("path");

module.exports = ({ env }) => {
  const client = env("DATABASE_CLIENT", "sqlite");

  const connections = {
    mysql: {
      connection: {
        connectionString: env("DATABASE_URL"),
        host: env("DATABASE_HOST", "localhost"),
        port: env.int("DATABASE_PORT", 3306),
        database: env("DATABASE_NAME", "strapi"),
        user: env("DATABASE_USERNAME", "strapi"),
        password: env("DATABASE_PASSWORD", "strapi"),
        ssl: env.bool("DATABASE_SSL", false) && {
          key: env("DATABASE_SSL_KEY", undefined),
          cert: env("DATABASE_SSL_CERT", undefined),
          ca: env("DATABASE_SSL_CA", undefined),
          capath: env("DATABASE_SSL_CAPATH", undefined),
          cipher: env("DATABASE_SSL_CIPHER", undefined),
          rejectUnauthorized: env.bool(
            "DATABASE_SSL_REJECT_UNAUTHORIZED",
            true
          ),
        },
      },
      pool: {
        min: env.int("DATABASE_POOL_MIN", 2),
        max: env.int("DATABASE_POOL_MAX", 10),
      },
    },
    mysql2: {
      connection: {
        host: env("DATABASE_HOST", "localhost"),
        port: env.int("DATABASE_PORT", 3306),
        database: env("DATABASE_NAME", "strapi"),
        user: env("DATABASE_USERNAME", "strapi"),
        password: env("DATABASE_PASSWORD", "strapi"),
        ssl: env.bool("DATABASE_SSL", false) && {
          key: env("DATABASE_SSL_KEY", undefined),
          cert: env("DATABASE_SSL_CERT", undefined),
          ca: env("DATABASE_SSL_CA", undefined),
          capath: env("DATABASE_SSL_CAPATH", undefined),
          cipher: env("DATABASE_SSL_CIPHER", undefined),
          rejectUnauthorized: env.bool(
            "DATABASE_SSL_REJECT_UNAUTHORIZED",
            true
          ),
        },
      },
      pool: {
        min: env.int("DATABASE_POOL_MIN", 2),
        max: env.int("DATABASE_POOL_MAX", 10),
      },
    },
    postgres: {
      connection: {
        connectionString: env("DATABASE_URL"),
        host: env("DATABASE_HOST", "localhost"),
        port: env.int("DATABASE_PORT", 5432),
        database: env("DATABASE_NAME", "strapi"),
        user: env("DATABASE_USERNAME", "strapi"),
        password: env("DATABASE_PASSWORD", "strapi"),
        ssl: env.bool("DATABASE_SSL", false) && {
          key: env("DATABASE_SSL_KEY", undefined),
          cert: env("DATABASE_SSL_CERT", undefined),
          ca: env("DATABASE_SSL_CA", undefined),
          capath: env("DATABASE_SSL_CAPATH", undefined),
          cipher: env("DATABASE_SSL_CIPHER", undefined),
          rejectUnauthorized: env.bool(
            "DATABASE_SSL_REJECT_UNAUTHORIZED",
            true
          ),
        },
        schema: env("DATABASE_SCHEMA", "public"),
      },
      pool: {
        min: env.int("DATABASE_POOL_MIN", 2),
        max: env.int("DATABASE_POOL_MAX", 10),
      },
    },
    sqlite: {
      connection: {
        filename: path.join(
          __dirname,
          "..",
          env("DATABASE_FILENAME", ".tmp/data.db")
        ),
      },
      useNullAsDefault: true,
    },
  };

  return {
    connection: {
      client,
      ...connections[client],
      acquireConnectionTimeout: env.int("DATABASE_CONNECTION_TIMEOUT", 60000),
    },
  };
};

[quote=“peuweb, post:52, topic:17412, full:true”]
At first, thanks for helping us.

My .env file i have the follow values:

DATABASE_CLIENT=mysql
DATABASE_HOST=my.custom.host
DATABASE_PORT=3306
DATABASE_NAME=database_name
DATABASE_USERNAME=database_username
DATABASE_PASSWORD=database_password

And here is my config/database.js file

const path = require("path");

module.exports = ({ env }) => {
  const client = env("DATABASE_CLIENT", "sqlite");

  const connections = {
    mysql: {
      connection: {
        connectionString: env("DATABASE_URL"),
        host: env("DATABASE_HOST", "localhost"),
        port: env.int("DATABASE_PORT", 3306),
        database: env("DATABASE_NAME", "strapi"),
        user: env("DATABASE_USERNAME", "strapi"),
        password: env("DATABASE_PASSWORD", "strapi"),
        ssl: env.bool("DATABASE_SSL", false) && {
          key: env("DATABASE_SSL_KEY", undefined),
          cert: env("DATABASE_SSL_CERT", undefined),
          ca: env("DATABASE_SSL_CA", undefined),
          capath: env("DATABASE_SSL_CAPATH", undefined),
          cipher: env("DATABASE_SSL_CIPHER", undefined),
          rejectUnauthorized: env.bool(
            "DATABASE_SSL_REJECT_UNAUTHORIZED",
            true
          ),
        },
      },
      pool: {
        min: env.int("DATABASE_POOL_MIN", 2),
        max: env.int("DATABASE_POOL_MAX", 10),
      },
    },
    mysql2: {
      connection: {
        host: env("DATABASE_HOST", "localhost"),
        port: env.int("DATABASE_PORT", 3306),
        database: env("DATABASE_NAME", "strapi"),
        user: env("DATABASE_USERNAME", "strapi"),
        password: env("DATABASE_PASSWORD", "strapi"),
        ssl: env.bool("DATABASE_SSL", false) && {
          key: env("DATABASE_SSL_KEY", undefined),
          cert: env("DATABASE_SSL_CERT", undefined),
          ca: env("DATABASE_SSL_CA", undefined),
          capath: env("DATABASE_SSL_CAPATH", undefined),
          cipher: env("DATABASE_SSL_CIPHER", undefined),
          rejectUnauthorized: env.bool(
            "DATABASE_SSL_REJECT_UNAUTHORIZED",
            true
          ),
        },
      },
      pool: {
        min: env.int("DATABASE_POOL_MIN", 2),
        max: env.int("DATABASE_POOL_MAX", 10),
      },
    },
    postgres: {
      connection: {
        connectionString: env("DATABASE_URL"),
        host: env("DATABASE_HOST", "localhost"),
        port: env.int("DATABASE_PORT", 5432),
        database: env("DATABASE_NAME", "strapi"),
        user: env("DATABASE_USERNAME", "strapi"),
        password: env("DATABASE_PASSWORD", "strapi"),
        ssl: env.bool("DATABASE_SSL", false) && {
          key: env("DATABASE_SSL_KEY", undefined),
          cert: env("DATABASE_SSL_CERT", undefined),
          ca: env("DATABASE_SSL_CA", undefined),
          capath: env("DATABASE_SSL_CAPATH", undefined),
          cipher: env("DATABASE_SSL_CIPHER", undefined),
          rejectUnauthorized: env.bool(
            "DATABASE_SSL_REJECT_UNAUTHORIZED",
            true
          ),
        },
        schema: env("DATABASE_SCHEMA", "public"),
      },
      pool: {
        min: env.int("DATABASE_POOL_MIN", 2),
        max: env.int("DATABASE_POOL_MAX", 10),
      },
    },
    sqlite: {
      connection: {
        filename: path.join(
          __dirname,
          "..",
          env("DATABASE_FILENAME", ".tmp/data.db")
        ),
      },
      useNullAsDefault: true,
    },
  };

  return {
    connection: {
      client,
      ...connections[client],
      acquireConnectionTimeout: env.int("DATABASE_CONNECTION_TIMEOUT", 60000),
    },
  };
};

Ps. I do not have any environment file that rewrites the database.js configurations

Facing this issue as well… Our config/database.js file look like this:

const path = require('path');

module.exports = ({ env }) => ({
  connection: {
    client: 'postgres',
    connection: {
      host: env('DATABASE_HOST'),
      port: env.int('DATABASE_PORT', 5432),
      database: env('DATABASE_NAME'),
      user: env('DATABASE_USERNAME'),
      password: env('DATABASE_PASSWORD'),
      ssl: env.bool('DATABASE_SSL', false),
    },
  }
});

And are you passing DATABASE_CLIENT when building the docker image.
When you start the container and it runs does it run with the correct database or does it show sqlite.

@chlec
Do you have multiple database.js files for environments or any config/env/X folders?

In the various Dockerfile scripts that I see in the message trail above, one - critical - thing seems to be missing. You must rebuild the Admin UI after the ‘yarn install’, or it is likely that you will use an old UI, whose configuration for content types does not match the content in the database. This can result in tables (content types) and fields ‘disappearing’.

Also, if you run Strapi in ‘development’ mode inside a container, then the whole ‘src’ folder must be made persistent, otherwise any changes that are made - e.g. by creating or editing a content type - will be ‘lost’ next time the container is restarted.

Strapi does not store its schema ‘in the database’ - it stores it in the ‘src’ folder and it ‘freezes’ it for production when you build the Admin UI.

1 Like

Hello.

I am not using DOCKER. Just a pure NODE on my server.

I’m using these lines to build the environment on my CI/CD Tool.

NODE_ENV=production yarn
NODE_ENV=production yarn build
NODE_ENV=production pm2 update ecosystems.config.js

Note. I’m using pm2 as main webserver.

Here is my config folder. I don’t have any ENV rewrite structure(config/env/production/).
image

I just have one .env file on my server.

On this week I’ll move my project to another server because I still want to use Strapi in my project.

Hello @Eventyret, I have only a production environment with the Postgres database, I am facing the same issue. I created a collection in a single type and inserted data from the production environment but sometimes after the deployment my data is removed from the collection, It sometimes happens not with every deployment. When I make my fields editable false from the configure view the data is not removed after deployment.

I had the same issue. Postgres db, no docker, database.js the same as mentioned above. Hosting at Render.
Strapi version v4.12.4
node version v18.13.0
All data disappeared without notification.

I got all my content erased as well. Fortunately just launching the site and only had a few posts. My situation was that I presumed I could have two instances of strapi targeting the same Azure mySQL db. I had a prod instance in Azure App Service. It was on “version 1” lets say of my schema. It was asleep because I have it on sleep to save azure money. I worked on my strapi content for a week running strapi locally, but targeting the Azure mySQL db. In addition to creating content types I also added content. In getting ready to deploy version this “version 2” schema, I went to check on my production strapi instance and incidentally started it up. It then deleted all my content. I was thinking it would just throw errors because it didn’t have the correct schema for working with the changed db, not wipe the tables. This deletion behavior is not intuitive, and should be documented. Please comment link to documentation if it does exist.

Overall you cannot have your dev and prod env strapi instances target the same db, even if you are working on a very small project, where you dont care if prod doesn’t work while you are changing the db via dev.

I see now that the latest prescribed path is to deploy to keep env dbs content in sync is with the newer data transfer feature Data transfer | Strapi Documentation

There are warnings everywhere in the docs about what I was doing :man_facepalming:, like Database migrations | Strapi Documentation where it says your tables will be deleted if the instance doesn’t know them:
image

To accommodate my lazy workflow I am setting runMigrations and forceMigration to false in the production env.

1 Like

Nice tip. Will try to force the parameters suggested. Thanks.