import { Database } from ".";

export const initializeSubjectTable = async (db: Database) => {
  await db.schema
    .createTable("subjects")
    .ifNotExists()
    .addColumn("id", "integer", (col) => col.primaryKey().notNull())
    .addColumn("reviewState", "text", (col) => col.notNull())
    .addColumn("createdAt", "text", (col) => col.notNull())
    .addColumn("updatedAt", "text", (col) => col.notNull())
    .addColumn("lastReportedAt", "text")
    .addColumn("lastReviewedBy", "text")
    .addColumn("lastReviewedAt", "text")
    .addColumn("takendown", "integer", (col) => col.notNull().defaultTo(0))
    .addColumn("subjectRepoHandle", "text")
    .addColumn("subjectBlobCids", "text")
    .addColumn("tags", "text")
    .addColumn("did", "text", (col) => col.notNull())
    .addColumn("recordPath", "text", (col) => col.notNull().defaultTo(""))
    .addColumn("lastAppealedAt", "text")
    .addColumn("suspendUntil", "text")
    .addColumn("muteUntil", "text")
    .addColumn("muteReportingUntil", "text")
    .addColumn("comment", "text")
    .execute();
};

export const initializeRepoTable = async (db: Database) => {
  await db.schema
    .createTable("repos")
    .ifNotExists()
    .addColumn("did", "text", (col) => col.primaryKey().notNull())
    .addColumn("handle", "text", (col) => col.notNull())
    .addColumn("ip", "text", (col) => col.notNull())
    .addColumn("profile", "jsonb")
    .addColumn("indexedAt", "text", (col) => col.notNull())
    .addColumn("email", "text", (col) => col.notNull())
    .addColumn("emailConfirmedAt", "text")
    .addColumn("threatSignatures", "text")
    .addColumn("labels", "jsonb")
    .execute();
};

export const initializeProfileTable = async (db: Database) => {
  await db.schema
    .createTable("profiles")
    .ifNotExists()
    .addColumn("did", "text", (col) => col.primaryKey().notNull()) // Primary Key
    .addColumn("handle", "text", (col) => col.notNull()) // Unique identifier
    .addColumn("displayName", "text") // Optional display name
    .addColumn("description", "text") // Optional description or bio
    .addColumn("avatar", "text") // URL or path to avatar image
    .addColumn("banner", "text") // URL or path to banner image
    .addColumn("followersCount", "integer") // Count of followers
    .addColumn("followsCount", "integer") // Count of accounts followed
    .addColumn("postsCount", "integer") // Count of posts
    .addColumn("associated", "jsonb") // JSON serialized ProfileAssociated
    .addColumn("joinedViaStarterPack", "jsonb") // JSON serialized StarterPackViewBasic
    .addColumn("indexedAt", "text") // Timestamp for indexing
    .addColumn("createdAt", "text") // Timestamp for creation
    .addColumn("viewer", "jsonb") // JSON serialized ViewerState
    .addColumn("labels", "jsonb") // JSON serialized array of labels
    .addColumn("pinnedPost", "jsonb") // JSON serialized pinned post reference
    .addColumn("extra", "jsonb") // JSON serialized extra data
    .addColumn("syncedAt", "text") // timestamp for when the profile was last synced
    .execute();
};

export const initializeEventTable = async (db: Database) => {
  await db.schema
    .createTable("events")
    .ifNotExists()
    .addColumn("id", "serial", (col) => col.primaryKey()) // Auto-incrementing ID
    .addColumn("action", "text", (col) => col.notNull()) // Action type
    .addColumn("subjectType", "text", (col) => col.notNull()) // Enforcing predefined subject types
    .addColumn("subjectDid", "text", (col) => col.notNull()) // Subject DID
    .addColumn("subjectUri", "text") // Optional subject URI
    .addColumn("subjectCid", "text") // Optional subject CID
    .addColumn("subjectBlobCids", "jsonb") // JSON array of CIDs
    .addColumn("subjectMessageId", "text") // Optional message ID
    .addColumn("createLabelVals", "text") // Optional label values
    .addColumn("negateLabelVals", "text") // Optional label negation
    .addColumn("comment", "text") // Optional comment
    .addColumn("createdAt", "text", (col) => col.notNull()) // Creation timestamp
    .addColumn("createdBy", "text", (col) => col.notNull()) // Created by user
    .addColumn("durationInHours", "integer") // Optional duration
    .addColumn("expiresAt", "text") // Optional expiration timestamp
    .addColumn("meta", "jsonb") // JSON metadata
    .addColumn("addedTags", "jsonb") // JSON array of added tags
    .addColumn("removedTags", "jsonb") // JSON array of removed tags
    .execute();
};

export const initializeRecordTable = async (db: Database) => {
  await db.schema
    .createTable("records")
    .ifNotExists()
    .addColumn("uri", "text", (col) => col.primaryKey().notNull())
    .addColumn("cid", "text", (col) => col.notNull())
    .addColumn("value", "jsonb", (col) => col.notNull())
    .addColumn("blobCids", "jsonb", (col) => col.notNull())
    .addColumn("indexedAt", "text", (col) => col.notNull())
    .addColumn("blobs", "jsonb", (col) => col.notNull())
    .addColumn("labels", "jsonb", (col) => col.notNull())
    .execute();
};
