using System.ComponentModel.DataAnnotations; using System.ComponentModel.DataAnnotations.Schema; using Microsoft.EntityFrameworkCore; using Microsoft.EntityFrameworkCore.Metadata.Builders; using J = System.Text.Json.Serialization.JsonPropertyNameAttribute; namespace Iceshrimp.Backend.Core.Database.Tables; [Table("drive_file")] [Index(nameof(IsLink))] [Index(nameof(Sha256))] [Index(nameof(UserId), nameof(FolderId), nameof(Id))] [Index(nameof(UserId))] [Index(nameof(UserHost))] [Index(nameof(Type))] [Index(nameof(IsSensitive))] [Index(nameof(FolderId))] [Index(nameof(PublicAccessKey))] [Index(nameof(CreatedAt))] [Index(nameof(AccessKey))] [Index(nameof(Uri))] [Index(nameof(ThumbnailAccessKey))] public class DriveFile : IEntity { /// /// The created date of the DriveFile. /// [Column("createdAt")] public DateTime CreatedAt { get; set; } /// /// The owner ID. /// [Column("userId")] [StringLength(32)] public string? UserId { get; set; } /// /// The host of owner. It will be null if the user in local. /// [Column("userHost")] [StringLength(512)] public string? UserHost { get; set; } /// /// The SHA256 hash of the DriveFile. /// [Column("sha256")] [StringLength(64)] public string? Sha256 { get; set; } /// /// The file name of the DriveFile. /// [Column("name")] [StringLength(256)] public string Name { get; set; } = null!; /// /// The content type (MIME) of the DriveFile. /// [Column("type")] [StringLength(128)] public string Type { get; set; } = null!; /// /// The file size (bytes) of the DriveFile. /// [Column("size")] public int Size { get; set; } /// /// The comment of the DriveFile. /// [Column("comment")] public string? Comment { get; set; } /// /// The any properties of the DriveFile. For example, it includes image width/height. /// [Column("properties", TypeName = "jsonb")] public FileProperties Properties { get; set; } = null!; [Column("storedInternal")] public bool StoredInternal { get; set; } /// /// The URL of the DriveFile. /// [Column("url")] [StringLength(512)] public string Url { get; set; } = null!; /// /// The URL of the thumbnail of the DriveFile. /// [Column("thumbnailUrl")] [StringLength(512)] public string? ThumbnailUrl { get; set; } /// /// The URL of the webpublic of the DriveFile. /// [Column("webpublicUrl")] [StringLength(512)] public string? PublicUrl { get; set; } [Column("accessKey")] [StringLength(256)] public string AccessKey { get; set; } = null!; [Column("thumbnailAccessKey")] [StringLength(256)] public string? ThumbnailAccessKey { get; set; } [Column("webpublicAccessKey")] [StringLength(256)] public string? PublicAccessKey { get; set; } /// /// The URI of the DriveFile. it will be null when the DriveFile is local. /// [Column("uri")] [StringLength(512)] public string? Uri { get; set; } [Column("src")] [StringLength(512)] public string? Src { get; set; } /// /// The parent folder ID. If null, it means the DriveFile is located in root. /// [Column("folderId")] [StringLength(32)] public string? FolderId { get; set; } /// /// Whether the DriveFile is NSFW. /// [Column("isSensitive")] public bool IsSensitive { get; set; } /// /// Whether the DriveFile is direct link to remote server. /// [Column("isLink")] public bool IsLink { get; set; } /// /// The BlurHash string. /// [Column("blurhash")] [StringLength(128)] public string? Blurhash { get; set; } [Column("thumbnailType")] [StringLength(128)] public string? ThumbnailMimeType { get; set; } [Column("webpublicType")] [StringLength(128)] public string? PublicMimeType { get; set; } [Column("requestHeaders", TypeName = "jsonb")] public Dictionary? RequestHeaders { get; set; } [Column("requestIp")] [StringLength(128)] public string? RequestIp { get; set; } [InverseProperty(nameof(Channel.Banner))] public virtual ICollection Channels { get; set; } = new List(); [ForeignKey(nameof(FolderId))] [InverseProperty(nameof(DriveFolder.DriveFiles))] public virtual DriveFolder? Folder { get; set; } [InverseProperty(nameof(MessagingMessage.File))] public virtual ICollection MessagingMessages { get; set; } = new List(); [InverseProperty(nameof(Page.EyeCatchingImage))] public virtual ICollection Pages { get; set; } = new List(); [ForeignKey(nameof(UserId))] [InverseProperty(nameof(Tables.User.DriveFiles))] public virtual User? User { get; set; } [InverseProperty(nameof(Tables.User.Avatar))] public virtual User? UserAvatar { get; set; } [InverseProperty(nameof(Tables.User.Banner))] public virtual User? UserBanner { get; set; } [NotMapped] public string RawAccessUrl => PublicUrl ?? Url; [NotMapped] public string RawThumbnailAccessUrl => ThumbnailUrl ?? PublicUrl ?? Url; [Key] [Column("id")] [StringLength(32)] public string Id { get; set; } = null!; public class FileProperties { [J("width")] public int? Width { get; set; } [J("height")] public int? Height { get; set; } } private class EntityTypeConfiguration : IEntityTypeConfiguration { public void Configure(EntityTypeBuilder entity) { entity.Property(e => e.Blurhash).HasComment("The BlurHash string."); entity.Property(e => e.Comment).HasComment("The comment of the DriveFile."); entity.Property(e => e.CreatedAt).HasComment("The created date of the DriveFile."); entity.Property(e => e.FolderId) .HasComment("The parent folder ID. If null, it means the DriveFile is located in root."); entity.Property(e => e.IsLink) .HasDefaultValue(false) .HasComment("Whether the DriveFile is direct link to remote server."); entity.Property(e => e.IsSensitive) .HasDefaultValue(false) .HasComment("Whether the DriveFile is NSFW."); entity.Property(e => e.Sha256).HasComment("The SHA256 hash of the DriveFile."); entity.Property(e => e.Name).HasComment("The file name of the DriveFile."); entity.Property(e => e.Properties) .HasDefaultValueSql("'{}'::jsonb") .HasComment("The any properties of the DriveFile. For example, it includes image width/height."); entity.Property(e => e.RequestHeaders).HasDefaultValueSql("'{}'::jsonb"); entity.Property(e => e.Size).HasComment("The file size (bytes) of the DriveFile."); entity.Property(e => e.ThumbnailUrl).HasComment("The URL of the thumbnail of the DriveFile."); entity.Property(e => e.Type).HasComment("The content type (MIME) of the DriveFile."); entity.Property(e => e.Uri) .HasComment("The URI of the DriveFile. it will be null when the DriveFile is local."); entity.Property(e => e.Url).HasComment("The URL of the DriveFile."); entity.Property(e => e.UserHost).HasComment("The host of owner. It will be null if the user in local."); entity.Property(e => e.UserId).HasComment("The owner ID."); entity.Property(e => e.PublicUrl).HasComment("The URL of the webpublic of the DriveFile."); entity.HasOne(d => d.Folder) .WithMany(p => p.DriveFiles) .OnDelete(DeleteBehavior.SetNull); entity.HasOne(d => d.User) .WithMany(p => p.DriveFiles) .OnDelete(DeleteBehavior.SetNull); } } }