Beispiel #1
0
    def test_edit_asset(self):
        with db.conn(settings['database']) as conn:
            assets_helper.create(conn, asset_x)

        with Browser() as browser:
            browser.visit('http://localhost:8080')
            wait_for_and_do(browser, '.edit-asset-button', lambda btn: btn.click())
            sleep(1)

            wait_for_and_do(browser, 'input[name="duration"]', lambda field: field.fill('333'))
            sleep(1)  # wait for new-asset panel animation

            wait_for_and_do(browser, '#add-form', lambda form: form.click())
            sleep(1)

            wait_for_and_do(browser, '#save-asset', lambda btn: btn.click())
            sleep(3)  # backend need time to process request

        with db.conn(settings['database']) as conn:
            assets = assets_helper.read(conn)

            self.assertEqual(len(assets), 1)
            asset = assets[0]

            self.assertEqual(asset['duration'], u'333')
Beispiel #2
0
    def test_rm_asset(self):
        with db.conn(settings['database']) as conn:
            assets_helper.create(conn, asset_x)

        with Browser() as browser:
            browser.visit('http://localhost:8080')

            wait_for_and_do(browser, '.delete-asset-button', lambda btn: btn.click())
            wait_for_and_do(browser, '.confirm-delete', lambda btn: btn.click())
            sleep(3)  # backend need time to process request

        with db.conn(settings['database']) as conn:
            assets = assets_helper.read(conn)
            self.assertEqual(len(assets), 0)
Beispiel #3
0
    def test_enable_asset(self):
        with db.conn(settings['database']) as conn:
            assets_helper.create(conn, asset_x)

        with Browser() as browser:
            browser.visit('http://localhost:8080')
            wait_for_and_do(browser, 'span[class="on"]', lambda btn: btn.click())
            sleep(3)  # backend need time to process request

        with db.conn(settings['database']) as conn:
            assets = assets_helper.read(conn)
            self.assertEqual(len(assets), 1)

            asset = assets[0]
            self.assertEqual(asset['is_enabled'], 1)
    def test_add_asset_streaming(self):
        with Browser() as browser:
            browser.visit(main_page_url)

            wait_for_and_do(browser, '#add-asset-button', lambda btn: btn.click())
            sleep(1)

            wait_for_and_do(browser, 'input[name="uri"]', lambda field: field.fill('rtmp://localhost:1935/app/video.flv'))
            sleep(1)

            wait_for_and_do(browser, '#add-form', lambda form: form.click())
            sleep(1)

            wait_for_and_do(browser, '#save-asset', lambda btn: btn.click())
            sleep(10)  # backend need time to process request

        with db.conn(settings['database']) as conn:
            assets = assets_helper.read(conn)

            self.assertEqual(len(assets), 1)
            asset = assets[0]

            self.assertEqual(asset['name'], u'rtmp://localhost:1935/app/video.flv')
            self.assertEqual(asset['uri'], u'rtmp://localhost:1935/app/video.flv')
            self.assertEqual(asset['mimetype'], u'streaming')
            self.assertEqual(asset['duration'], settings['default_streaming_duration'])
Beispiel #5
0
    def test_add_asset_url(self):
        with Browser() as browser:
            browser.visit('http://localhost:8080')

            wait_for_and_do(browser, '#add-asset-button', lambda btn: btn.click())
            sleep(1)
            wait_for_and_do(browser, 'input[name="uri"]', lambda field: field.fill('http://example.com'))
            wait_for_and_do(browser, 'input[name="duration"]', lambda field: field.fill('30'))
            sleep(1)
            wait_for_and_do(browser, '#add-form', lambda form: form.click())
            sleep(1)

            wait_for_and_do(browser, '#save-asset', lambda btn: btn.click())
            sleep(3)  # backend need time to process request

        with db.conn(settings['database']) as conn:
            assets = assets_helper.read(conn)

            self.assertEqual(len(assets), 1)
            asset = assets[0]

            self.assertEqual(asset['name'], u'http://example.com')
            self.assertEqual(asset['uri'], u'http://example.com')
            self.assertEqual(asset['mimetype'], u'webpage')
            self.assertEqual(asset['duration'], u'30')
Beispiel #6
0
    def get(self, asset_id):
        with db.conn(settings['database']) as conn:
            asset = assets_helper.read(conn, asset_id)

        if isinstance(asset, list):
            raise Exception('Invalid asset ID provided')

        if path.isfile(asset['uri']):
            filename = asset['name']

            with open(asset['uri'], 'rb') as f:
                content = f.read()

            mimetype = guess_type(filename)[0]
            if not mimetype:
                mimetype = 'application/octet-stream'

            result = {
                'type': 'file',
                'filename': filename,
                'content': b64encode(content),
                'mimetype': mimetype
            }
        else:
            result = {
                'type': 'url',
                'url': asset['uri']
            }

        return result
    def test_add_two_assets_upload(self):
        video_file = '/tmp/video.flv'
        image_file = '/tmp/image.png'

        with Browser() as browser:
            browser.visit(main_page_url)

            browser.find_by_id('add-asset-button').click()
            sleep(1)

            wait_for_and_do(browser, 'a[href="#tab-file_upload"]', lambda tab: tab.click())
            wait_for_and_do(browser, 'input[name="file_upload"]', lambda input: input.fill(image_file))
            wait_for_and_do(browser, 'input[name="file_upload"]', lambda input: input.fill(video_file))

            sleep(3)  # backend need time to process request

        with db.conn(settings['database']) as conn:
            assets = assets_helper.read(conn)

            self.assertEqual(len(assets), 2)

            self.assertEqual(assets[0]['name'], u'image.png')
            self.assertEqual(assets[0]['mimetype'], u'image')
            self.assertEqual(assets[0]['duration'], settings['default_duration'])

            self.assertEqual(assets[1]['name'], u'video.flv')
            self.assertEqual(assets[1]['mimetype'], u'video')
            self.assertEqual(assets[1]['duration'], u'54')
Beispiel #8
0
    def test_add_asset_video_upload(self):
        video_file = '/tmp/video.mov'

        with Browser() as browser:
            browser.visit('http://localhost:8080')

            browser.find_by_id('add-asset-button').click()
            sleep(1)

            wait_for_and_do(browser, 'a[href="#tab-file_upload"]', lambda tab: tab.click())
            wait_for_and_do(browser, 'input[name="file_upload"]', lambda input: input.fill(video_file))
            sleep(1)  # wait for new-asset panel animation

            wait_for_and_do(browser, '#add-form', lambda form: form.click())
            sleep(1)

            wait_for_and_do(browser, '#save-asset', lambda btn: btn.click())
            sleep(3)  # backend need time to process request

        with db.conn(settings['database']) as conn:
            assets = assets_helper.read(conn)

            self.assertEqual(len(assets), 1)
            asset = assets[0]

            self.assertEqual(asset['name'], u'video.mov')
            self.assertEqual(asset['mimetype'], u'video')
            self.assertEqual(asset['duration'], u'33')
    def test_disable_asset(self):
        with db.conn(settings['database']) as conn:
            _asset_x = asset_x.copy()
            _asset_x['is_enabled'] = 1
            assets_helper.create(conn, _asset_x)

        with Browser() as browser:
            browser.visit(main_page_url)

            wait_for_and_do(browser, 'span[class="off"]', lambda btn: btn.click())
            sleep(3)  # backend need time to process request

        with db.conn(settings['database']) as conn:
            assets = assets_helper.read(conn)
            self.assertEqual(len(assets), 1)

            asset = assets[0]
            self.assertEqual(asset['is_enabled'], 0)
Beispiel #10
0
 def delete(self, asset_id):
     with db.conn(settings['database']) as conn:
         asset = assets_helper.read(conn, asset_id)
         try:
             if asset['uri'].startswith(settings['assetdir']):
                 remove(asset['uri'])
         except OSError:
             pass
         assets_helper.delete(conn, asset_id)
         return '', 204  # return an OK with no content
Beispiel #11
0
def setup():
    global HOME, arch, db_conn
    HOME = getenv('HOME', '/home/pi')
    arch = machine()

    signal(SIGUSR1, sigusr1)

    load_settings()
    db_conn = db.conn(settings['database'])

    sh.mkdir(SCREENLY_HTML, p=True)
    html_templates.black_page(BLACK_PAGE)
Beispiel #12
0
    def post(self):
        asset = prepare_asset_v1_2(request)
        if url_fails(asset['uri']):
            raise Exception("Could not retrieve file. Check the asset URL.")
        with db.conn(settings['database']) as conn:
            assets = assets_helper.read(conn)
            ids_of_active_assets = [x['asset_id'] for x in assets if x['is_active']]

            asset = assets_helper.create(conn, asset)

            if asset['is_active']:
                ids_of_active_assets.insert(asset['play_order'], asset['asset_id'])
            assets_helper.save_ordering(conn, ids_of_active_assets)
            return assets_helper.read(conn, asset['asset_id']), 201
Beispiel #13
0
    def get(self):
        collector = ZmqCollector.get_instance()

        publisher = ZmqPublisher.get_instance()
        publisher.send_to_viewer('current_asset_id')

        collector_result = collector.recv_json(2000)
        current_asset_id = collector_result.get('current_asset_id')

        if not current_asset_id:
            return []

        with db.conn(settings['database']) as conn:
            return assets_helper.read(conn, current_asset_id)
Beispiel #14
0
    def test_reorder_asset(self):
        with db.conn(settings['database']) as conn:
            _asset_x = asset_x.copy()
            _asset_x['is_enabled'] = 1
            assets_helper.create(conn, _asset_x)
            assets_helper.create(conn, asset_y)

        with Browser() as browser:
            browser.visit('http://localhost:8080')

            asset_x_for_drag = browser.find_by_id(asset_x['asset_id'])
            sleep(1)

            asset_y_to_reorder = browser.find_by_id(asset_y['asset_id'])
            asset_x_for_drag.drag_and_drop(asset_y_to_reorder)
            sleep(3)  # backend need time to process request

        with db.conn(settings['database']) as conn:
            x = assets_helper.read(conn, asset_x['asset_id'])
            y = assets_helper.read(conn, asset_y['asset_id'])

            self.assertEqual(x['play_order'], 0)
            self.assertEqual(y['play_order'], 1)
Beispiel #15
0
    def put(self, asset_id):
        asset = prepare_asset_v1_2(request, asset_id)
        with db.conn(settings['database']) as conn:
            assets = assets_helper.read(conn)
            ids_of_active_assets = [x['asset_id'] for x in assets if x['is_active']]

            asset = assets_helper.update(conn, asset_id, asset)

            try:
                ids_of_active_assets.remove(asset['asset_id'])
            except ValueError:
                pass
            if asset['is_active']:
                ids_of_active_assets.insert(asset['play_order'], asset['asset_id'])

            assets_helper.save_ordering(conn, ids_of_active_assets)
            return assets_helper.read(conn, asset_id)
Beispiel #16
0
 def get(self):
     with db.conn(settings['database']) as conn:
         assets = assets_helper.read(conn)
         return assets
Beispiel #17
0
@app.route('/static_with_mime/<string:path>')
@auth_basic
def static_with_mime(path):
    mimetype = request.args['mime'] if 'mime' in request.args else 'auto'
    return send_from_directory(directory='static', filename=path, mimetype=mimetype)


if __name__ == "__main__":
    # Make sure the asset folder exist. If not, create it
    if not path.isdir(settings['assetdir']):
        mkdir(settings['assetdir'])
    # Create config dir if it doesn't exist
    if not path.isdir(settings.get_configdir()):
        makedirs(settings.get_configdir())

    with db.conn(settings['database']) as conn:
        with db.cursor(conn) as cursor:
            cursor.execute(queries.exists_table)
            if cursor.fetchone() is None:
                cursor.execute(assets_helper.create_assets_table)

    config = {
        'bind': '{}:{}'.format(LISTEN, PORT),
        'threads': 2,
        'timeout': 20
    }

    class GunicornApplication(Application):
        def init(self, parser, opts, args):
            return config
Beispiel #18
0
def playlist_order():
    with db.conn(settings['database']) as conn:
        assets_helper.save_ordering(conn,
                                    request.POST.get('ids', '').split(','))
 def setUp(self):
     self.old_db_path = settings.settings['database']
     viewer.db_conn = db.conn(':memory:')
     with db.commit(viewer.db_conn) as cursor:
         cursor.execute(assets_helper.create_assets_table)
Beispiel #20
0
 def setUp(self):
     self.assertEmpty = functools.partial(self.assertEqual, [])
     self.conn = db.conn(':memory:')
     with db.commit(self.conn) as cursor:
         cursor.execute(assets_helper.create_assets_table)
Beispiel #21
0
 def post(self):
     asset = prepare_asset(request, unique_name=True)
     if url_fails(asset['uri']):
         raise Exception("Could not retrieve file. Check the asset URL.")
     with db.conn(settings['database']) as conn:
         return assets_helper.create(conn, asset), 201
Beispiel #22
0
 def post(self):
     asset = prepare_asset(request)
     if url_fails(asset['uri']):
         raise Exception("Could not retrieve file. Check the asset URL.")
     with db.conn(settings['database']) as conn:
         return assets_helper.create(conn, asset), 201
Beispiel #23
0
 def get(self, asset_id):
     with db.conn(settings['database']) as conn:
         return assets_helper.read(conn, asset_id)
Beispiel #24
0
 def put(self, asset_id):
     with db.conn(settings['database']) as conn:
         return assets_helper.update(conn, asset_id, prepare_asset(request))
 def setUp(self):
     self.assertEmpty = functools.partial(self.assertEqual, [])
     self.conn = db.conn(':memory:')
     with db.commit(self.conn) as cursor:
         cursor.execute(assets_helper.create_assets_table)
Beispiel #26
0
 def setUp(self):
     self.old_db_path = settings.settings['database']
     viewer.db_conn = db.conn(':memory:')
     with db.commit(viewer.db_conn) as cursor:
         cursor.execute(assets_helper.create_assets_table)
Beispiel #27
0
def api_assets():
    with db.conn(settings['database']) as conn:
        assets = assets_helper.read(conn)
        return make_json_response(assets)
Beispiel #28
0
def api_assets():
    with db.conn(settings['database']) as conn:
        assets = assets_helper.read(conn)
        return make_json_response(assets)
Beispiel #29
0
def static_with_mime(path):
    mimetype = request.args['mime'] if 'mime' in request.args else 'auto'
    return send_from_directory(directory='static',
                               filename=path,
                               mimetype=mimetype)


if __name__ == "__main__":
    # Make sure the asset folder exist. If not, create it
    if not path.isdir(settings['assetdir']):
        mkdir(settings['assetdir'])
    # Create config dir if it doesn't exist
    if not path.isdir(settings.get_configdir()):
        makedirs(settings.get_configdir())

    with db.conn(settings['database']) as conn:
        with db.cursor(conn) as cursor:
            cursor.execute(queries.exists_table)
            if cursor.fetchone() is None:
                cursor.execute(assets_helper.create_assets_table)

    config = {
        'bind': '{}:{}'.format(LISTEN, PORT),
        'threads': 2,
        'timeout': 20
    }

    class GunicornApplication(Application):
        def init(self, parser, opts, args):
            return config
Beispiel #30
0
def prepare_asset_v1_2(request_environ, asset_id=None, unique_name=False):
    data = json.loads(request_environ.data)

    def get(key):
        val = data.get(key, '')
        if isinstance(val, unicode):
            return val.strip()
        elif isinstance(val, basestring):
            return val.strip().decode('utf-8')
        else:
            return val

    if not all([get('name'),
                get('uri'),
                get('mimetype'),
                str(get('is_enabled')),
                get('start_date'),
                get('end_date')]):
        raise Exception(
            "Not enough information provided. Please specify 'name', 'uri', 'mimetype', 'is_enabled', 'start_date' and 'end_date'.")

    name = get('name')
    if unique_name:
        with db.conn(settings['database']) as conn:
            names = assets_helper.get_names_of_assets(conn)
        if name in names:
            i = 1
            while True:
                new_name = '%s-%i' % (name, i)
                if new_name in names:
                    i += 1
                else:
                    name = new_name
                    break

    asset = {
        'name': name,
        'mimetype': get('mimetype'),
        'is_enabled': get('is_enabled'),
        'nocache': get('nocache')
    }

    uri = get('uri')

    if uri.startswith('/'):
        if not path.isfile(uri):
            raise Exception("Invalid file path. Failed to add asset.")
    else:
        if not validate_url(uri):
            raise Exception("Invalid URL. Failed to add asset.")

    if not asset_id:
        asset['asset_id'] = uuid.uuid4().hex
        if uri.startswith('/'):
            rename(uri, path.join(settings['assetdir'], asset['asset_id']))
            uri = path.join(settings['assetdir'], asset['asset_id'])

    if 'youtube_asset' in asset['mimetype']:
        uri, asset['name'], asset['duration'] = download_video_from_youtube(uri, asset['asset_id'])
        asset['mimetype'] = 'video'
        asset['is_processing'] = 1

    asset['uri'] = uri

    if "video" in asset['mimetype']:
        if get('duration') == 'N/A' or int(get('duration')) == 0:
            asset['duration'] = int(get_video_duration(uri).total_seconds())
    elif get('duration'):
        # Crashes if it's not an int. We want that.
        asset['duration'] = int(get('duration'))
    else:
        asset['duration'] = 10

    asset['play_order'] = get('play_order') if get('play_order') else 0

    asset['skip_asset_check'] = int(get('skip_asset_check')) if int(get('skip_asset_check')) else 0

    # parse date via python-dateutil and remove timezone info
    asset['start_date'] = date_parser.parse(get('start_date')).replace(tzinfo=None)
    asset['end_date'] = date_parser.parse(get('end_date')).replace(tzinfo=None)

    return asset
Beispiel #31
0
 def post(self):
     with db.conn(settings['database']) as conn:
         assets_helper.save_ordering(conn,
                                     request.form.get('ids', '').split(','))
Beispiel #32
0
 def get(self):
     with db.conn(settings['database']) as conn:
         assets = assets_helper.read(conn)
         return assets
Beispiel #33
0
def prepare_asset_v1_2(request_environ, asset_id=None, unique_name=False):
    data = json.loads(request_environ.data)

    def get(key):
        val = data.get(key, '')
        if isinstance(val, unicode):
            return val.strip()
        elif isinstance(val, basestring):
            return val.strip().decode('utf-8')
        else:
            return val

    if not all([
            get('name'),
            get('uri'),
            get('mimetype'),
            str(get('is_enabled')),
            get('start_date'),
            get('end_date')
    ]):
        raise Exception(
            "Not enough information provided. Please specify 'name', 'uri', 'mimetype', 'is_enabled', 'start_date' and 'end_date'."
        )

    name = get('name')
    if unique_name:
        with db.conn(settings['database']) as conn:
            names = assets_helper.get_names_of_assets(conn)
        if name in names:
            i = 1
            while True:
                new_name = '%s-%i' % (name, i)
                if new_name in names:
                    i += 1
                else:
                    name = new_name
                    break

    asset = {
        'name': name,
        'mimetype': get('mimetype'),
        'is_enabled': get('is_enabled'),
        'nocache': get('nocache')
    }

    uri = get('uri')

    if uri.startswith('/'):
        if not path.isfile(uri):
            raise Exception("Invalid file path. Failed to add asset.")
    else:
        if not validate_url(uri):
            raise Exception("Invalid URL. Failed to add asset.")

    if not asset_id:
        asset['asset_id'] = uuid.uuid4().hex
        if uri.startswith('/'):
            rename(uri, path.join(settings['assetdir'], asset['asset_id']))
            uri = path.join(settings['assetdir'], asset['asset_id'])

    if 'youtube_asset' in asset['mimetype']:
        uri, asset['name'], asset['duration'] = download_video_from_youtube(
            uri, asset['asset_id'])
        asset['mimetype'] = 'video'
        asset['is_processing'] = 1

    asset['uri'] = uri

    if "video" in asset['mimetype']:
        if get('duration') == 'N/A' or int(get('duration')) == 0:
            asset['duration'] = int(get_video_duration(uri).total_seconds())
    elif get('duration'):
        # Crashes if it's not an int. We want that.
        asset['duration'] = int(get('duration'))
    else:
        asset['duration'] = 10

    asset['play_order'] = get('play_order') if get('play_order') else 0

    asset['skip_asset_check'] = int(get('skip_asset_check')) if int(
        get('skip_asset_check')) else 0

    # parse date via python-dateutil and remove timezone info
    asset['start_date'] = date_parser.parse(
        get('start_date')).replace(tzinfo=None)
    asset['end_date'] = date_parser.parse(get('end_date')).replace(tzinfo=None)

    return asset
Beispiel #34
0
 def put(self, asset_id):
     with db.conn(settings['database']) as conn:
         return assets_helper.update(conn, asset_id, prepare_asset(request))
Beispiel #35
0
def playlist_order():
    with db.conn(settings['database']) as conn:
        assets_helper.save_ordering(conn, request.POST.get('ids', '').split(','))
Beispiel #36
0
 def setUp(self):
     with db.conn(settings['database']) as conn:
         assets = assets_helper.read(conn)
         for asset in assets:
             assets_helper.delete(conn, asset['asset_id'])
Beispiel #37
0
 def get(self, asset_id):
     with db.conn(settings['database']) as conn:
         return assets_helper.read(conn, asset_id)
Beispiel #38
0
 def post(self):
     with db.conn(settings['database']) as conn:
         assets_helper.save_ordering(conn, request.form.get('ids', '').split(','))
Beispiel #39
0
 def setUp(self):
     with db.conn(settings['database']) as conn:
         assets = assets_helper.read(conn)
         for asset in assets:
             assets_helper.delete(conn, asset['asset_id'])