2020-02-05 14:51:46 +01:00
package resolvers
import (
"context"
2020-07-10 18:52:18 +02:00
"github.com/pkg/errors"
2020-02-05 14:51:46 +01:00
api "github.com/viktorstrate/photoview/api/graphql"
"github.com/viktorstrate/photoview/api/graphql/auth"
"github.com/viktorstrate/photoview/api/graphql/models"
2020-02-14 13:31:44 +01:00
"github.com/viktorstrate/photoview/api/scanner"
2020-11-28 17:31:19 +01:00
"gorm.io/gorm"
2020-02-05 14:51:46 +01:00
)
2020-07-10 14:26:19 +02:00
func ( r * queryResolver ) MyMedia ( ctx context . Context , filter * models . Filter ) ( [ ] * models . Media , error ) {
2020-02-09 14:21:53 +01:00
user := auth . UserFromContext ( ctx )
if user == nil {
return nil , errors . New ( "unauthorized" )
}
2020-10-13 17:27:28 +02:00
filterSQL , err := filter . FormatSQL ( "media" )
2020-02-09 15:26:59 +01:00
if err != nil {
return nil , err
}
2020-11-28 17:31:19 +01:00
var media [ ] * models . Media
err = r . Database . Raw ( `
2020-07-10 14:26:19 +02:00
SELECT media . * FROM media , album
2020-11-28 17:31:19 +01:00
WHERE media . album_id = albums . id AND albums . owner_id = ?
2020-07-10 14:26:19 +02:00
AND media . media_id IN (
2020-11-28 17:31:19 +01:00
SELECT media_id FROM media_url WHERE media_url . media_id = media . id
2020-02-27 16:26:53 +01:00
)
2020-11-28 17:31:19 +01:00
` + filterSQL , user . ID ) . Scan ( & media ) . Error
2020-02-09 14:21:53 +01:00
if err != nil {
return nil , err
}
2020-11-28 17:31:19 +01:00
return media , nil
2020-02-05 14:51:46 +01:00
}
2020-07-10 14:26:19 +02:00
func ( r * queryResolver ) Media ( ctx context . Context , id int ) ( * models . Media , error ) {
2020-02-05 14:51:46 +01:00
user := auth . UserFromContext ( ctx )
if user == nil {
return nil , auth . ErrUnauthorized
}
2020-11-28 17:31:19 +01:00
var media models . Media
err := r . Database . Raw ( `
2020-07-10 14:26:19 +02:00
SELECT media . * FROM media
2020-11-28 17:31:19 +01:00
JOIN albums ON media . album_id = albums . id
2020-07-10 14:26:19 +02:00
WHERE media . media_id = ? AND album . owner_id = ?
AND media . media_id IN (
SELECT media_id FROM media_url WHERE media_url . media_id = media . media_id
2020-02-27 16:26:53 +01:00
)
2020-11-28 17:31:19 +01:00
` , id , user . ID ) . Scan ( & media ) . Error
2020-02-05 14:51:46 +01:00
if err != nil {
2020-07-10 18:52:18 +02:00
return nil , errors . Wrap ( err , "could not get media by media_id and user_id from database" )
2020-02-05 14:51:46 +01:00
}
2020-11-28 17:31:19 +01:00
return & media , nil
2020-02-05 14:51:46 +01:00
}
2020-09-27 20:52:09 +02:00
func ( r * queryResolver ) MediaList ( ctx context . Context , ids [ ] int ) ( [ ] * models . Media , error ) {
user := auth . UserFromContext ( ctx )
if user == nil {
return nil , auth . ErrUnauthorized
}
if len ( ids ) == 0 {
return nil , errors . New ( "no ids provided" )
}
2020-11-28 17:31:19 +01:00
var media [ ] * models . Media
// err := r.Database.
// Select("media.*").
// Joins("Album").
// Where("media.id IN ?", ids).
// Where("album.owner_id = ?", user.ID).
// Where("media.id IN (?)", r.Database.Model(&models.MediaURL{}).Select("media_id").Where("media_url.media_id = media.id")).
// Scan(&media).Error
2020-09-27 20:52:09 +02:00
2020-11-28 17:31:19 +01:00
err := r . Database . Raw ( `
2020-09-27 20:52:09 +02:00
SELECT media . * FROM media
2020-11-28 17:31:19 +01:00
JOIN albums AS album ON media . album_id = album . id
WHERE media . media_id IN ? AND album . owner_id = ?
2020-09-27 20:52:09 +02:00
AND media . media_id IN (
SELECT media_id FROM media_url WHERE media_url . media_id = media . media_id
)
2020-11-28 17:31:19 +01:00
` , ids , user . ID ) . Error
2020-09-27 20:52:09 +02:00
if err != nil {
2020-11-28 17:31:19 +01:00
return nil , errors . Wrap ( err , "could not get media list by media_id and user_id from database" )
2020-09-27 20:52:09 +02:00
}
return media , nil
}
2020-07-10 14:26:19 +02:00
type mediaResolver struct {
2020-02-05 14:51:46 +01:00
* Resolver
}
2020-07-10 14:26:19 +02:00
func ( r * Resolver ) Media ( ) api . MediaResolver {
return & mediaResolver { r }
2020-02-05 14:51:46 +01:00
}
2020-11-28 17:31:19 +01:00
func ( r * mediaResolver ) Shares ( ctx context . Context , media * models . Media ) ( [ ] * models . ShareToken , error ) {
var shareTokens [ ] * models . ShareToken
2020-11-28 21:49:33 +01:00
if err := r . Database . Where ( "media_id = ?" , media . ID ) . Find ( & shareTokens ) . Error ; err != nil {
2020-11-28 17:31:19 +01:00
return nil , errors . Wrapf ( err , "get shares for media (%s)" , media . Path )
2020-02-11 15:36:12 +01:00
}
2020-11-28 17:31:19 +01:00
return shareTokens , nil
2020-02-10 12:05:58 +01:00
}
2020-11-28 17:31:19 +01:00
func ( r * mediaResolver ) Downloads ( ctx context . Context , media * models . Media ) ( [ ] * models . MediaDownload , error ) {
2020-02-21 22:42:39 +01:00
2020-11-28 17:31:19 +01:00
var mediaUrls [ ] * models . MediaURL
if err := r . Database . Where ( "media_id = ?" , media . ID ) . Find ( & mediaUrls ) . Error ; err != nil {
return nil , errors . Wrapf ( err , "get downloads for media (%s)" , media . Path )
2020-02-21 22:42:39 +01:00
}
2020-07-10 14:26:19 +02:00
downloads := make ( [ ] * models . MediaDownload , 0 )
2020-02-21 22:42:39 +01:00
2020-07-10 14:26:19 +02:00
for _ , url := range mediaUrls {
2020-02-21 22:42:39 +01:00
var title string
switch {
2020-07-10 12:58:11 +02:00
case url . Purpose == models . MediaOriginal :
2020-02-21 22:42:39 +01:00
title = "Original"
case url . Purpose == models . PhotoThumbnail :
title = "Small"
case url . Purpose == models . PhotoHighRes :
title = "Large"
2020-07-11 16:42:27 +02:00
case url . Purpose == models . VideoThumbnail :
title = "Video thumbnail"
case url . Purpose == models . VideoWeb :
title = "Web optimized video"
2020-02-21 22:42:39 +01:00
}
2020-07-10 14:26:19 +02:00
downloads = append ( downloads , & models . MediaDownload {
2020-08-11 22:34:42 +02:00
Title : title ,
MediaURL : url ,
2020-02-21 22:42:39 +01:00
} )
}
2020-02-10 12:05:58 +01:00
return downloads , nil
2020-02-09 12:53:21 +01:00
}
2020-11-28 17:31:19 +01:00
func ( r * mediaResolver ) HighRes ( ctx context . Context , media * models . Media ) ( * models . MediaURL , error ) {
var url models . MediaURL
err := r . Database .
2020-11-30 21:29:49 +01:00
Where ( "media_id = ?" , media . ID ) .
2020-11-28 17:31:19 +01:00
Where ( "purpose = ? OR (purpose = ? AND content_type IN ?)" , models . PhotoHighRes , models . MediaOriginal , scanner . WebMimetypes ) .
First ( & url ) . Error
2020-02-05 14:51:46 +01:00
2020-02-09 14:21:53 +01:00
if err != nil {
2020-11-28 17:31:19 +01:00
if errors . Is ( err , gorm . ErrRecordNotFound ) {
2020-07-11 14:21:10 +02:00
return nil , nil
} else {
2020-11-28 17:31:19 +01:00
return nil , errors . Wrapf ( err , "could not query high-res (%s)" , media . Path )
2020-07-11 14:21:10 +02:00
}
2020-02-09 14:21:53 +01:00
}
2020-02-05 14:51:46 +01:00
2020-11-28 17:31:19 +01:00
return & url , nil
2020-02-05 14:51:46 +01:00
}
2020-11-28 17:31:19 +01:00
func ( r * mediaResolver ) Thumbnail ( ctx context . Context , media * models . Media ) ( * models . MediaURL , error ) {
var url models . MediaURL
err := r . Database .
2020-11-30 21:29:49 +01:00
Where ( "media_id = ?" , media . ID ) .
2020-11-28 17:31:19 +01:00
Where ( "purpose = ? OR purpose = ?" , models . PhotoThumbnail , models . VideoThumbnail ) .
First ( & url ) . Error
2020-02-05 14:51:46 +01:00
2020-02-09 14:21:53 +01:00
if err != nil {
2020-11-28 17:31:19 +01:00
return nil , errors . Wrapf ( err , "could not query thumbnail (%s)" , media . Path )
2020-02-09 14:21:53 +01:00
}
2020-02-05 14:51:46 +01:00
2020-11-28 17:31:19 +01:00
return & url , nil
2020-02-05 14:51:46 +01:00
}
2020-11-28 17:31:19 +01:00
func ( r * mediaResolver ) VideoWeb ( ctx context . Context , media * models . Media ) ( * models . MediaURL , error ) {
var url models . MediaURL
err := r . Database .
2020-11-30 21:29:49 +01:00
Where ( "media_id = ?" , media . ID ) .
2020-11-28 17:31:19 +01:00
Where ( "purpose = ?" , models . VideoWeb ) .
First ( & url ) . Error
2020-07-11 15:57:58 +02:00
if err != nil {
2020-11-28 17:31:19 +01:00
if errors . Is ( err , gorm . ErrRecordNotFound ) {
2020-07-11 16:42:27 +02:00
return nil , nil
} else {
2020-11-28 17:31:19 +01:00
return nil , errors . Wrapf ( err , "could not query video web-format url (%s)" , media . Path )
2020-07-11 16:42:27 +02:00
}
2020-07-11 15:57:58 +02:00
}
2020-11-28 17:31:19 +01:00
return & url , nil
2020-07-11 15:57:58 +02:00
}
2020-11-28 17:31:19 +01:00
// func (r *mediaResolver) Album(ctx context.Context, media *models.Media) (*models.Album, error) {
2020-02-05 14:51:46 +01:00
2020-11-28 17:31:19 +01:00
// r.Database.Model(&media).Joins("Album")
2020-02-24 23:56:28 +01:00
2020-11-28 17:31:19 +01:00
// row := r.Database.QueryRow("SELECT album.* from media JOIN album ON media.album_id = album.album_id WHERE media_id = ?", media.MediaID)
// return models.NewAlbumFromRow(row)
// }
2020-02-24 23:56:28 +01:00
2020-11-28 17:31:19 +01:00
// func (r *mediaResolver) Exif(ctx context.Context, obj *models.Media) (*models.MediaEXIF, error) {
// row := r.Database.QueryRow("SELECT media_exif.* FROM media NATURAL JOIN media_exif WHERE media.media_id = ?", obj.MediaID)
2020-06-17 18:00:58 +02:00
2020-11-28 17:31:19 +01:00
// exif, err := models.NewMediaExifFromRow(row)
// if err != nil {
// if errors.Is(err, gorm.ErrRecordNotFound) {
// return nil, nil
// } else {
// return nil, errors.Wrapf(err, "could not get exif of media from database")
// }
// }
2020-07-12 14:17:49 +02:00
2020-11-28 17:31:19 +01:00
// return exif, nil
// }
2020-07-12 14:17:49 +02:00
2020-11-28 17:31:19 +01:00
// func (r *mediaResolver) VideoMetadata(ctx context.Context, obj *models.Media) (*models.VideoMetadata, error) {
// row := r.Database.QueryRow("SELECT video_metadata.* FROM media JOIN video_metadata ON media.video_metadata_id = video_metadata.metadata_id WHERE media.media_id = ?", obj.MediaID)
// metadata, err := models.NewVideoMetadataFromRow(row)
// if err != nil {
// if errors.Is(err, gorm.ErrRecordNotFound) {
// return nil, nil
// } else {
// return nil, errors.Wrapf(err, "could not get video metadata of media from database")
// }
// }
// return metadata, nil
// }
2020-07-12 14:17:49 +02:00
2020-07-10 14:26:19 +02:00
func ( r * mutationResolver ) FavoriteMedia ( ctx context . Context , mediaID int , favorite bool ) ( * models . Media , error ) {
2020-06-17 18:00:58 +02:00
user := auth . UserFromContext ( ctx )
2020-11-28 17:31:19 +01:00
var media models . Media
2020-06-17 18:00:58 +02:00
2020-11-28 17:31:19 +01:00
if err := r . Database . Joins ( "Album" ) . Where ( "Album.owner_id = ?" , user . ID ) . First ( & media , mediaID ) . Error ; err != nil {
2020-06-17 18:00:58 +02:00
return nil , err
}
2020-11-28 17:31:19 +01:00
media . Favorite = favorite
if err := r . Database . Save ( & media ) . Error ; err != nil {
2020-07-10 18:52:18 +02:00
return nil , errors . Wrap ( err , "failed to update media favorite on database" )
2020-06-19 15:34:29 +02:00
}
2020-11-28 17:31:19 +01:00
return & media , nil
2020-06-17 18:00:58 +02:00
}