Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

MySQL datamodel not matching prisma2 introspect generated schema #1497

Closed
hatchli opened this issue Jan 31, 2020 · 4 comments
Closed

MySQL datamodel not matching prisma2 introspect generated schema #1497

hatchli opened this issue Jan 31, 2020 · 4 comments
Assignees
Milestone

Comments

@hatchli
Copy link

hatchli commented Jan 31, 2020

I am using an RDS MySQL database. The only difference in the SQL schema from that provided in the "Get Started" doc is removal of WITH TIME ZONE on created_at for the posts table.

CREATE TABLE users (
	user_id SERIAL PRIMARY KEY NOT NULL,
	name VARCHAR(256),
	email VARCHAR(256) UNIQUE NOT NULL
);

CREATE TABLE posts (
	post_id SERIAL PRIMARY KEY NOT NULL,
	created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
	title VARCHAR(256) NOT NULL,
	content TEXT,
	author_id INTEGER REFERENCES users(user_id) 
);

CREATE TABLE profiles (
	profile_id SERIAL PRIMARY KEY NOT NULL,
	bio TEXT,
	user_id INTEGER NOT NULL REFERENCES users(user_id) 
);

When I run introspect on prisma2, I get the following data model schema in schema.prisma:

model posts {
  author_id  Int?
  content    String?
  created_at DateTime?
  post_id    Int       @id
  title      String
}

model profiles {
  bio        String?
  profile_id Int     @id
  user_id    Int
}

model users {
  email   String  @unique
  name    String?
  user_id Int     @id
}

This is quite different from the schema that is supposed to be generated, per the "Get Starting" docs. Primarily, the relations seem to be missing entirely:

model posts {
  author_id  users?
  content    String?
  created_at DateTime?
  post_id    Int       @id
  title      String
}

model profiles {
  bio        String?
  profile_id Int     @id
  user_id    users
}

model users {
  email      String     @unique
  name       String?
  user_id    Int        @id
  postses    posts[]
  profileses profiles[]
}

What exactly am I doing wrong here? I suppose this might be a MySQL specific issue?

@janpio janpio added this to the Preview 22 milestone Jan 31, 2020
@janpio
Copy link
Member

janpio commented Jan 31, 2020

I assume you refer to https://github.com/prisma/prisma2/blob/master/docs/getting-started.md#2-introspect-your-database-to-generate-a-data-model?

I think the documentation might just be missing the foreign key definitions - which leads to the generated schema to also miss all relations unfortunately.

We should fix this as soon as possible.

@hatchli
Copy link
Author

hatchli commented Jan 31, 2020

That's correct @janpio

I figured it out in the meanwhile after referencing the MySQL docs for a while.
The following SQL schema:

CREATE TABLE users (
	user_id SERIAL PRIMARY KEY,
	name VARCHAR(256),
	email VARCHAR(256) UNIQUE NOT NULL
);

CREATE TABLE posts (
	post_id SERIAL PRIMARY KEY,
	created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
	title VARCHAR(256) NOT NULL,
	content TEXT,
	author_id BIGINT UNSIGNED NOT NULL,
    INDEX author_index (author_id),
	FOREIGN KEY (author_id) REFERENCES users(user_id)
    ON DELETE CASCADE
);

CREATE TABLE profiles (
	profile_id SERIAL PRIMARY KEY,
	bio TEXT,
	user_id BIGINT UNSIGNED NOT NULL,
    INDEX user_index (user_id),
	FOREIGN KEY (user_id) REFERENCES users(user_id)
    ON DELETE CASCADE
);

Creates the following datamodel schema in prisma.schema:

model posts {
  content    String?
  created_at DateTime?
  post_id    Int       @id
  title      String
  author_id  users
}

model profiles {
  bio        String?
  profile_id Int     @id
  user_id    users
}

model users {
  email      String     @unique
  name       String?
  user_id    Int        @id
  postses    posts[]
  profileses profiles[]
}

Which from what I can tell restores the relationships, with the only difference being that an author_id is not null, versus the docs allowing for a null author_id.

@hatchli hatchli closed this as completed Jan 31, 2020
@janpio
Copy link
Member

janpio commented Jan 31, 2020

Thanks! Let's leave this issue open though until the problem is really fixed in the docs. We can now pretty much just take what you discovered.

@janpio janpio reopened this Jan 31, 2020
@nikolasburk
Copy link
Member

Thanks for all the info @hatchli, that's super helpful! I've adjusted the SQL schema in the docs to contain an explicit declaration of the FOREIGN KEY constraint:

CREATE TABLE users (
  user_id SERIAL PRIMARY KEY NOT NULL,
  name VARCHAR(256),
  email VARCHAR(256) UNIQUE NOT NULL
);

CREATE TABLE posts (
  post_id SERIAL PRIMARY KEY NOT NULL,
  created_at TIMESTAMP WITH TIME ZONE DEFAULT CURRENT_TIMESTAMP,
  title VARCHAR(256) NOT NULL,
  content TEXT,
  author_id INTEGER,
  FOREIGN KEY (author_id) REFERENCES users(user_id) 
);

CREATE TABLE profiles (
  profile_id SERIAL PRIMARY KEY NOT NULL,
  bio TEXT,
  user_id INTEGER NOT NULL,
  FOREIGN KEY (user_id) REFERENCES users(user_id)
);

This issue occurred because there seem to be differences in how foreign keys are defined in MySQL and Postgres. With Postgres, you can actually omit the FOREIGN KEY declaration, that's why the initial version also worked. For a bit more context, check out this question on Stackoverflow.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants