summaryrefslogtreecommitdiff
path: root/cron/handler.py
blob: 68214edbfbd996dde9fb183bc0ebd804a187b1c7 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
import boto3
import json
import re

from datetime import datetime, timedelta
from ftplib import FTP
from io import BytesIO
from os import environ


class GeshemUpdate():

    def __init__(self):
        self.ftp = None
        self.s3 = boto3.client('s3')
        self.BUCKET = 'imgs.geshem.space'
        self.IMG_PREFIX = 'imgs/'

    def __enter__(self):
        self.init_ftp()
        return self

    def __exit__(self, *args):
        if self.ftp:
            self.ftp.quit()

    def init_ftp(self):
        host = environ.get("FTP_HOST")
        username = environ.get("FTP_USERNAME")
        password = environ.get("FTP_PASSWORD")
        if all([host, username, password]):
            self.ftp = FTP(host)
            self.ftp.login(username, password)
            self.ftp.cwd("From_IMS")
            print("Logged in to FTP server...")

    def get_latest_ftp_images(self):
        return sorted(list(self.ftp.nlst()))[-10:]

    def get_latest_bucket_keys(self):
        latest_keys = []
        yesterday = (datetime.utcnow().date() - timedelta(days=1)).strftime('%Y%m%d')

        try:
            latest_imgs = self.s3.list_objects_v2(Bucket=self.BUCKET, Prefix=self.IMG_PREFIX, StartAfter=self.IMG_PREFIX + yesterday)['Contents']
            latest_keys = [i['Key'] for i in latest_imgs]
        except KeyError:
            pass

        return latest_keys

    def fetch_missing_images(self):
        ftp_imgs = self.get_latest_ftp_images()
        s3_imgs = self.get_latest_bucket_keys()
        updated = False

        for img in ftp_imgs:
            key = self.key_from_filename(img)
            if key not in s3_imgs:
                self.fetch_image(img, key)
                updated = True

        return updated

    def fetch_image(self, img_name, key):
        img = BytesIO()
        print(f"Downloading {img_name} from FTP")
        self.ftp.retrbinary(f"RETR {img_name}", img.write)
        img.seek(0)
        print(f"Uploading to {key}")
        self.s3.put_object(Bucket=self.BUCKET, Key=key, Body=img, ContentType='image/png', CacheControl='public, max-age=31536000')

    def key_from_filename(self, filename):
        _name, date = filename.split(".")[0].split("_")
        res = 280
        # date conversion isn't really needed but we do it anyway just to make sure
        dt = datetime.strptime(date, '%Y%m%d%H%M')
        d = dt.strftime('%Y%m%d')
        t = dt.strftime('%H%M')
        return f'{self.IMG_PREFIX}{d}/{t}/{res}.png'

    def generate_json(self):
        latest_keys = self.get_latest_bucket_keys()
        keys = sorted(list(filter(lambda k: k.endswith('280.png'), latest_keys)))[-10:]
        index = json.dumps({'280': keys})
        self.s3.put_object(Bucket=self.BUCKET, Key='imgs.json', Body=index, ContentType='application/json', CacheControl='public, max-age=60')

    def run(self):
        updated = self.fetch_missing_images()
        if updated:
            self.generate_json()
        return f"Updated: {updated}"


def update(event, context):
    with GeshemUpdate() as gu:
        res = gu.run()
    body = {
        "message": "SUCCESS: \n" + res,
        "input": event
    }
    response = {
        "statusCode": 200,
        "body": json.dumps(body)
    }
    return response


if __name__ == "__main__":
    with GeshemUpdate() as gu:
        res = gu.run()