]> git.immae.eu Git - github/Chocobozzz/PeerTube.git/blobdiff - server/models/video/tag.ts
Don't expose constants directly in initializers/
[github/Chocobozzz/PeerTube.git] / server / models / video / tag.ts
index 6d79a55756ad212f84977a383be0757525d950dd..b39621eaf4a4daf55cdb93a3a5f0fe903674bd7f 100644 (file)
@@ -1,10 +1,11 @@
 import * as Bluebird from 'bluebird'
-import { Transaction } from 'sequelize'
+import * as Sequelize from 'sequelize'
 import { AllowNull, BelongsToMany, Column, CreatedAt, Is, Model, Table, UpdatedAt } from 'sequelize-typescript'
 import { isVideoTagValid } from '../../helpers/custom-validators/videos'
 import { throwIfNotValid } from '../utils'
 import { VideoModel } from './video'
 import { VideoTagModel } from './video-tag'
+import { VideoPrivacy, VideoState } from '../../../shared/models/videos'
 
 @Table({
   tableName: 'tag',
@@ -36,7 +37,7 @@ export class TagModel extends Model<TagModel> {
   })
   Videos: VideoModel[]
 
-  static findOrCreateTags (tags: string[], transaction: Transaction) {
+  static findOrCreateTags (tags: string[], transaction: Sequelize.Transaction) {
     if (tags === null) return []
 
     const tasks: Bluebird<TagModel>[] = []
@@ -47,11 +48,10 @@ export class TagModel extends Model<TagModel> {
         },
         defaults: {
           name: tag
-        }
+        },
+        transaction
       }
 
-      if (transaction) query['transaction'] = transaction
-
       const promise = TagModel.findOrCreate(query)
         .then(([ tagInstance ]) => tagInstance)
       tasks.push(promise)
@@ -59,4 +59,23 @@ export class TagModel extends Model<TagModel> {
 
     return Promise.all(tasks)
   }
+
+  // threshold corresponds to how many video the field should have to be returned
+  static getRandomSamples (threshold: number, count: number): Bluebird<string[]> {
+    const query = 'SELECT tag.name FROM tag ' +
+      'INNER JOIN "videoTag" ON "videoTag"."tagId" = tag.id ' +
+      'INNER JOIN video ON video.id = "videoTag"."videoId" ' +
+      'WHERE video.privacy = $videoPrivacy AND video.state = $videoState ' +
+      'GROUP BY tag.name HAVING COUNT(tag.name) >= $threshold ' +
+      'ORDER BY random() ' +
+      'LIMIT $count'
+
+    const options = {
+      bind: { threshold, count, videoPrivacy: VideoPrivacy.PUBLIC, videoState: VideoState.PUBLISHED },
+      type: Sequelize.QueryTypes.SELECT
+    }
+
+    return TagModel.sequelize.query(query, options)
+                    .then(data => data.map(d => d.name))
+  }
 }