π μ€μκ° μΈκΈ° κ²μλ¬Όμ μ΄λ€ μμΌλ‘ ꡬνν΄μΌ νλ κ³ λ―Όμ λ§μ΄ νλ€.
νμ¬ νλ‘μ νΈμ μΈκΈ° κ²μλ¬Όμμ κ°λ₯΄λ κΈ°μ€μ λκ°μ§κ° μλ€.
μ’μμμ μ‘°νμμ΄λ€.class Article(models.Model): user = models.ForeignKey(User, on_delete=models.CASCADE, related_name='article_user') category = models.ForeignKey(Hobby, on_delete=models.CASCADE, related_name='article_category') title = models.CharField(max_length=500) content = models.TextField() article_image = models.ImageField(upload_to=rename_imagefile_to_uuid, blank=True) created_at = models.DateTimeField(auto_now_add=True) updated_at = models.DateTimeField(auto_now=True) like = models.ManyToManyField(User, blank=True, related_name='article_like') views = models.BigIntegerField(default=0)
likeμ views κ° μ’μμμ μ‘°νμ μΈλ° ν΄λΉ νλ κΈ°μ€μΌλ‘ ν 10 κ²μλ¬Όμ 보μ¬μ€λ€λ©΄ orderbyλ‘ views.pyμμ μ λ ¬ν΄μ νλ‘ νΈλ‘ 보λ΄μ£Όλ©΄ λμΌ κ²μ΄λ€.
νμ§λ§ νλ² μΈκΈ° κ²μλ¬Όμ μκ° μ νμ΄ μλ€λ©΄ 1λ¬, 1λ κΉμ§ κ° μ μμ κ²μ΄λ€.
ν΄μ created_atμΌλ‘ μκ° λ°°μ¨μ μ‘°μ νλ€λ©΄ λ°κΏ μ μκ² λ€κ³ μκ°νμλ€.λν μλ‘κ³ μΉ¨ λλ§λ€ μΈκΈ° κ²μλ¬Όμ μ μλ₯Ό λ§€κΈ°κ³ μΆμ§ μμλ€. μμ²μ΄ μμλλ§λ€ μ°μ°μ΄ μμκ²μ΄κ³ μλ²μ λΆλ΄μ μ£ΌκΈ° μ«μκΈ° λλ¬Έμ΄λ€
κ·Έλμ μκ°νκ² django crontabμ μ΄μ©νμ¬ νΉμ νμΌμ 30λΆλ§λ€ μ€νμμΌ μΈκΈ° κ²μκΈ μμ΄λλ€μ μ λ ¬νμ¬ json νμΌλ‘ μ μ₯μ ν΄λμΌλ©΄ μμ²μ΄ λ€μ΄μ¬λ json νμΌλ§ μ½μ΄μ λΏλ €μ£Όλ©΄ λμ§μλ? λΌκ³ μκ°μ νμ¬ μΌλ¨!
μ½λλ₯Ό μ§λ΄€λ€.articles app μ μμλ‘ articlecron.pyλ₯Ό λ§λ ν μλμ κ°μ΄ μμ±νμλ€.
from datetime import datetime, timedelta from .models import Article from django.db.models import Q import os, json from pathlib import Path # if __name__ == "__main__": def get_score(): category_score_dict = {1: 20, 2: 20, 3: 20, 4: 20, 5: 20, 6: 20, 7: 20, 8: 20, 9: 20} # 1 : μΆκ΅¬ 2 : μΌκ΅¬ 3: μκ° 4: κ²μ(λ‘€) # κ³Ό κ°μμμΌλ‘ μ·¨λ―Έ νλ«νΌμ΄μ§λ§ μ΄λμλ μΈκΈ°μλ κ²μκΈμ΄λ # μΉ΄ν κ³ λ¦¬κ° μμ μ μμ΄ μΈκΈ°μλ μΉ΄ν κ³ λ¦¬λ§ μ 체 # μΈκΈ° κ²μκΈμ μ¬λΌκ°λ©΄ λΆκ³΅ν νλ―λ‘ categoryλ³ # μ μλ₯Ό κΈ°λ³Έμ μΌλ‘ μ‘μμ£Όμλ€. like_multiple = 1.2 # μ’μμ κ°μμ λ°λ₯Έ μ μμ΄λ€. # μ’μμ μ μλ μ‘°νμλ³΄λ€ ν¨μ¬ λμμΌ λλ€κ³ μκ°νμ§λ§ # μμ§ μ€κ³ λ¨κ³μ΄κΈ° λλ¬Έμ λλ΅μ μΌλ‘ μ ν΄λμλ€. view_multiple = 1 # μ‘°νμ κ°μμ λ°λ₯Έ μ μμ΄λ€. time_multiple = 0.2 # μκ°μ λ°λ₯Έ μ μμ΄λ€ μλμμ μ€λͺ νκ² λ€. current_time = datetime.now() # μκ°μ λ°λ₯Έ μ μλ₯Ό λ§€κΈΈ κ²μ΄κΈ°μ νμ¬ μκ°μ # μ΄κΈ°ν μμΌλμλ€. # μ·¨λ―Έ μΉ΄ν κ³ λ¦¬λ³ μ μ def score(obj) -> int: # κ²μκΈ μ€λΈμ νΈκ° λ€μ΄μ€λ©΄ μ μλ₯Ό λ§€κΈ°λ ν¨μμ΄λ€. result = 1 result *= category_score_dict[obj.category.id] # μμμ μ€λͺ ν μΉ΄ν κ³ λ¦¬λ³ μ μμ΄λ€. result *= obj.like.count() * like_multiple # μ’μμλ many to many field μ¬μ countλ₯Ό ν΄μ£Όμ΄μ # μ’μμ κ°μλ₯Ό κ°μ Έμ¨ ν λ°°μλ₯Ό κ³±ν΄μ£Όμλ€. result *= obj.views * view_multiple # μ‘°νμ μ μμ΄λ€. hour_diff_sec = (current_time - obj.created_at).total_seconds() / 3600 # νμ¬ μκ°μμ κ²μκΈμ΄ μμ±λ μκ°μ λΊ ν # total_seconds() ν¨μλ₯Ό μ΄μ©νλ©΄ μ΄κ° λμ¨λ€. # λ΄κ° μνλ κ²μ μκ°μ΄κΈ° λλ¬Έμ λΆ μ ν¬ν¨νμ¬ # 3600μΌλ‘ λλμ΄μ£Όλ©΄ κΈ μμ± μκ°λΆν° νμ¬μκ°κΉμ§ # λͺμκ° μ§λ¬λμ§ λμ¨λ€ # (10 - μκ°λ°°μ * μκ°μ°¨μ΄(hours)) μκ°λΉ 0.2 λ°°μ μ°¨μ΄ # ex) 1μκ° -> 9.8 , 2μκ° -> 9.6 return result * (10 - (time_multiple * hour_diff_sec)) # μ exampleκ³Ό κ°μ΄ μκ°λ³λ‘ 0.2 μ λ μ°¨μ΄λ₯Ό μ£Όκ³ μΆμ΄ # μκ° λ°°μλ₯Ό 0.2λ‘ μ§μ νμλ€. # μμ κ°μ λ°©μμΌλ‘ μ μλ₯Ό λ§€κΈ°λ©΄ μ€λλ κ²μλ¬Όμ # μμ²λ μ‘°νμμ μ’μμλ₯Ό μ§μν΄μ λ°μμΌ μ€μκ° # top κ²μκΈμ μ¬λΌκ° μ μμκ²μ΄λ€. article_obj = Article.objects.filter( Q(created_at__gte=(datetime.now() - timedelta(days=2))) & Q(updated_at__gte=(datetime.now() - timedelta(days=2)))) # update_atμ λΉΌμ€λ λ κ±°κ°μ§λ§ μ΄κΈ° μμ± μ # μμ λκ²λ ν¬ν¨νμ λΌλ μκ°μΌλ‘ μΌλ¨μ ν¬ν¨μμΌλ³΄μλ€. # νμ§λ§ μ μλ₯Ό λ§€κΈ°λ ν¨μμμ μ μ©μ΄ λμ§ μκΈ°μ μ§κΈμ # μΈλͺ¨ μλ μ½λμ΄λ€. # μ μ½λλ νμ¬ μκ°λΆν° μ΄ν μμ μμ±λ κ²μκΈμ κ°μ Έμ€λ μ½λμ΄λ€. article_score_id_list = [(x, score(x)) for x in article_obj] # μ΅μ’ μ μΌλ‘ νμΌμ μ μ₯λλ κ°μ idλ§ λμ΄μΌ νμ§λ§ μ μ # κΈ°μ€μΌλ‘ μ λ ¬μ μνκΈ° λλ¬Έμ μμλ‘ # (κ²μκΈ μ€λΈμ νΈ, κ²μκΈ μ μ) λ‘ λ§λ€μ΄μ£Όμλ€. article_score_id_list.sort(key=lambda x:x[1], reverse=True) # μ μ κΈ°μ€μΌλ‘ μ λ ¬ result = {} result_id = [article_score_id_list[x][0].id for x in range(len(article_score_id_list))] # νμΌμ μ μ₯νκΈ° μν΄ μ μ κΈ°μ€μΌλ‘ μ λ ¬λ 리μ€νΈμμ # μμ΄λ κ°λ§ κ°μ Έμμ λ΄μμ€λ€. result['result'] = result_id BASE_DIR = Path(__file__).resolve().parent.parent article_lank_file = os.path.join(BASE_DIR, 'article_lank.json') with open(article_lank_file, 'w') as f: json.dump(result, f, indent=4) # json ννλ‘ μ μ₯ν΄μ€λ€.
get_score() ν¨μλ λμ€μ main ν¨μλ‘ λ°λμ΄ cron tabμμ μ€νμν¬ κ²μ΄λ€.
ν μ€νΈ κ²°κ³Ό νμΌ μμ±κΉμ§ μ λλ©° viewμμ κ°μ Έμ€λ λ‘μ§μ μμ§ μμ±νμ§ μμλ€.
κ°μ Έμμ λΏλ €μ£Όλ건 μ½λ€..γ γ crontabμΌλ‘ 30λΆλ§λ€ μ€νμμΌμ£Όλ ν μ€νΈλ₯Ό ν΄λ³΄μμΌ νλλ° linux νκ²½μμλ§ κ°λ₯νκΈ° λλ¬Έμ μΌλ¨μ import νμ¬ ν¨μλ₯Ό νΈμΆνλ μμΌλ‘ μμ μμ±νμλ€.
λ€μμ£Όμ λ°°ν¬μ λμμ ν μ€νΈλ₯Ό νλ €κ³ νλ€.νμμ crontabμ μμ μ μ¬μ©ν΄λ³΄μκΈ° λλ¬Έμ ν¬κ² λ¬Έμ μμ΄ νΈλ€λ§ ν μ μμ κ² κ°λ€.
μ€μ μ¬μ΄νΈμμλ λμ± λ³΅μ‘ν λ‘μ§μΌλ‘ μ μλ₯Ό λ§€κΈ°κ² μ§λ§, λλ μ μ°, μνκ³Όκ° μλκΈ° λλ¬Έμ... λ‘μ§μ μΈμ λ μ§ λ°κΎΈλ©΄ λλκΉ μκ°λλ λλ‘ λ§λ€μ΄λ³΄κ³ μΆμ΄μ μμ±ν΄ 보μλ€.
μ΄μ workshop λΆλΆλ μμ±ν΄μΌμ§...!
μ€λ λ!