Exemplo n.º 1
0
 def close(self):
     for obj in (self.watcher, self.player, self.sources, self.audiolib,
                 self.videolib, self.webradio):
         if obj is not None:
             obj.close()
     Session.commit()
     Session.remove()
Exemplo n.º 2
0
 def save(self):
     db_list = Session.query(StaticMediaList)\
                      .filter(StaticMediaList.name == "__"+self.source)\
                      .one()
     db_list.items = []
     for entry in self.medialist:
         db_list.items.append(StaticMediaListItem(media_id=entry["m_id"]))
     Session.commit()
Exemplo n.º 3
0
 def new_func(*args, **kwargs):
     self = args[0]
     source = Session.query(WebradioSource)\
                     .filter(WebradioSource.name == self.NAME)\
                     .one()
     res = func(self, source, *args[1:], **kwargs)
     self._update_state()
     Session.commit()
     return res
Exemplo n.º 4
0
Arquivo: rpc.py Projeto: niol/deejayd
 def erase(self, pl_ids):
     if len(pl_ids) > 0:
         magic_or_static = with_polymorphic(MediaList, "*")
         pls = Session.query(magic_or_static)\
                      .filter(MediaList.id.in_(pl_ids))\
                      .all()
         for pl in pls:
             Session.delete(pl)
         Session.commit()
         self.dispatch_signame('recpls.listupdate')
Exemplo n.º 5
0
    def set_rating(self, ft, rating):
        if int(rating) not in list(range(0, 5)):
            raise DeejaydError(_("Bad rating value"))

        q = Session.query(self.OBJECT_CLASS)
        if ft is not None:
            q = q.filter(ft.get_filter(self.OBJECT_CLASS))
        for m in q.all():
            m.rating = rating
        Session.commit()
Exemplo n.º 6
0
    def __init__(self):
        super(_BaseWebradioSource, self).__init__()

        source = Session.query(WebradioSource)\
                        .filter(WebradioSource.name == self.NAME)\
                        .one_or_none()
        if source is None:
            source = WebradioSource(name=self.NAME)
            Session.add(source)
            Session.commit()
        self.load_state()
Exemplo n.º 7
0
 def load_state(self):
     st_name = "%s_state" % self.state_name
     s = Session.query(State) \
                .filter(State.name == st_name) \
                .one_or_none()
     if s is None:
         s = State(name=st_name)
         s.state = self.initial_state
         Session.add(s)
         Session.commit()
     self.state = s.state
Exemplo n.º 8
0
    def tearDown(self):
        self.deejayd.player.stop()
        self.deejayd.audiopls.clear()
        self.deejayd.videopls.clear()
        self.deejayd.audioqueue.clear()
        # remove recorded playlist
        pl_list = self.deejayd.recpls.get_list()
        self.deejayd.recpls.erase([pl["pl_id"] for pl in pl_list])
        # remove recorded webradio
        self.deejayd.webradio.source_clear_webradios("local")

        # close session
        Session.commit()
        Session.remove()
Exemplo n.º 9
0
    def save(self, pls_name):
        pls = Session.query(StaticMediaList)\
                     .filter(StaticMediaList.name == pls_name)\
                     .one_or_none()
        if pls is None:
            pls = StaticMediaList(name=pls_name)
            Session.add(pls)
        pls.items = [
            StaticMediaListItem(media_id=it["m_id"])
            for it in self._playlist.get()
        ]

        Session.commit()
        self.dispatch_signame('recpls.listupdate')
        return {"playlist_id": pls.id}
Exemplo n.º 10
0
    def __init__(self, start_inotify=True, library_update=True):
        super(DeejayDaemonCore, self).__init__()
        config = DeejaydConfig()

        self.player = player.init(config)
        self.put_sub_handler('player', self.player)

        self.audiolib, self.videolib, self.watcher = library.init(self.player,
                                                                  config)
        self.put_sub_handler('audiolib', self.audiolib)
        if self.videolib is not None:
            self.put_sub_handler('videolib', self.videolib)

        self.recpls = DeejaydRecordedPlaylist(self.audiolib)
        self.put_sub_handler('recpls', self.recpls)

        # add audio queue/playlist and video playlist
        self.sources = sources.init(self.player, self.audiolib,
                                    self.videolib, config)
        for source in list(self.sources.sources.values()):
            self.put_sub_handler(source.name, source)
            setattr(self, source.name, source)

        # add webradio if player can play http stream
        if self.player.is_supported_uri("http"):
            self.webradio = DeejaydWebradio(self.player)
            self.put_sub_handler('webradio', self.webradio)
        else:
            log.err(_("Player is not able to play http streams"))
            self.webradio = None

        if library_update:
            self.audiolib.update()
            if self.videolib is not None:
                self.videolib.update()

        # enable JSON-RPC introspection
        self.put_sub_handler('introspection', JSONRPCIntrospection(self))

        # start inotify thread when we are sure that all init stuff are ok
        if self.watcher and start_inotify:
            log.debug(_("Start inotify watcher"))
            self.watcher.start()
        # record changes and close session after the initialization
        Session.commit()
        Session.remove()
Exemplo n.º 11
0
    def __update_media(self, attrs):
        session = Session()
        video_or_song = with_polymorphic(Media, [Song, Video])
        m_obj = Session.query(video_or_song)\
                       .filter(Media.m_id == self.media["m_id"])\
                       .one_or_none()

        if m_obj is None:
            log.debug('media with id %d is gone, was probably deleted. '
                      'Ignoring media update.' % self.media["m_id"])
            return

        for key in attrs:
            setattr(m_obj, key, attrs[key])
            self.media[key] = attrs[key]
        session.commit()
        Session.remove()
Exemplo n.º 12
0
Arquivo: rpc.py Projeto: niol/deejayd
    def create(self, name, p_type):
        if name == "":
            raise DeejaydError(_("Set a playlist name"))
        if p_type not in ("static", "magic"):
            raise DeejaydError(_("playlist type has to be 'static' or 'magic'"))

        pls = Session.query(MediaList)\
                     .filter(MediaList.name == name)\
                     .one_or_none()
        if pls is not None:
            raise DeejaydError(_("This playlist already exists"))

        pl_cls = p_type == "static" and StaticMediaList or MagicMediaList
        pls = pl_cls(name=name)
        Session.add(pls)
        Session.commit()
        self.dispatch_signame('recpls.listupdate')
        return {"pl_id": pls.id, "name": name, "type": p_type}
Exemplo n.º 13
0
    def lineReceived(self, line):
        # use str instead of bytes to decode json commands
        # and return answer
        line = line.strip(b"\r").decode("utf-8")
        delimiter = self.delimiter.decode("utf-8")

        try:
            parsed = loads_request(line)
            args, function_path = parsed['params'], parsed["method"]
            if function_path.startswith("signal"):
                # it's a command linked with this connection
                method = function_path.split(self.separator, 1)[1]
                function = self.get_function(method)
            elif function_path == "close":
                function = self.close
            else:
                function = self.deejayd_core.get_function(function_path)
        except Fault as f:
            try:
                r_id = parsed["id"]
            except:
                r_id = None
            ans = JSONRPCResponse(f, r_id)
        else:
            # explicitly init session for this request
            Session()
            try:
                result = function(*args)
                Session.commit()
            except Exception as ex:
                Session.rollback()
                if not isinstance(ex, Fault):
                    log.err(traceback.format_exc())
                    result = Fault(self.FAILURE, _("error, see deejayd log"))
                else:
                    result = ex
            finally:
                Session.remove()
            ans = JSONRPCResponse(result, parsed["id"])

        self.send_buffer(ans.to_json()+delimiter)
        if self.__need_to_close:
            self.transport.loseConnection()
            self.__need_to_close = False
Exemplo n.º 14
0
Arquivo: rpc.py Projeto: niol/deejayd
        def load_playlist_func(self, pl_id, *__args, **__kw):
            if pls_type == "static":
                pls = Session.query(StaticMediaList).get(pl_id)
            elif pls_type == "magic":
                all_ft = with_polymorphic(Filter, "*", flat=True)
                pls = Session.query(MagicMediaList)\
                             .options(subqueryload(
                                 MagicMediaList.filters.of_type(all_ft))
                                )\
                             .filter(MagicMediaList.id == pl_id)\
                             .one()
            if pls is None:
                raise DeejaydError(_("Playlist %s not found") % str(pl_id))
            rs = func(self, pls, *__args, **__kw)

            if rs is True:
                Session.commit()
                self.dispatch_signame('recpls.update', pl_id=pl_id)
                return None
            return rs
Exemplo n.º 15
0
    def walk_directory(self, walk_root, force=False):
        walk_root = os.path.join(self.root_path, walk_root)
        walk_root = walk_root.rstrip("/")
        walked_folders = []
        # cache all medias recorded in database
        media_dict = {}
        for m in Session.query(self.OBJECT_CLASS).all():
            media_dict[m.get_path()] = m

        for root, subdirs, files in pathutils.walk(walk_root):
            root = root.rstrip("/")
            log.debug('library: update crawling %s' % root)
            if os.path.basename(root).startswith("."):
                continue  # skip hidden folder

            folder = self._get_folder(root)
            if folder is None:
                folder = LibraryFolder(library_id=self.library_id,
                                       path=root,
                                       name=os.path.basename(root))
                Session.add(folder)
            self.parse_files(folder, files, media_dict, force)

            subdirs_obj = self.get_subdirs(folder, subdirs)
            for sd in subdirs_obj:
                sd.parent_folder = folder
            walked_folders.append(root)

        # clean library
        Session.query(LibraryFolder) \
               .filter(LibraryFolder.library_id == self.library_id) \
               .filter(LibraryFolder.path.notin_(walked_folders)) \
               .delete(synchronize_session='fetch')
        if len(media_dict) > 0:
            db_media_ids = [media_dict[k].m_id for k in media_dict]
            erased_files = Session.query(self.OBJECT_CLASS) \
                            .filter(self.OBJECT_CLASS.m_id.in_(db_media_ids)) \
                            .all()
            for f in erased_files:
                Session.delete(f)
        Session.commit()
Exemplo n.º 16
0
    def __init__(self, source, pl_id):
        self.source = source
        self.repeat = False
        self.plmedia_id = 0
        self.pl_id = pl_id
        self.time_length = 0

        # load recorded playlist if exist
        db_list = Session.query(StaticMediaList)\
                         .filter(StaticMediaList.name == "__"+source)\
                         .one_or_none()
        if db_list is None:
            db_list = StaticMediaList(name="__" + source)
            Session.add(db_list)
            Session.commit()
        self.medialist = [
            PlaylistEntry(self, self.__get_next_id(), i.media, self.source)
            for i in db_list.items if i.media is not None
        ]
        self.time_length = reduce(lambda t, m: t + m["length"], self.medialist,
                                  0)
Exemplo n.º 17
0
    def process_event(self, ignore, filepath, mask, library, dir_path):
        # Raised events use real paths, and in the libraries, paths follow
        # symlinks on directories. Therefore, paths must be fixed to use
        # symlinks before being passed on to the library. This is why
        # the library dir_path is passed and used here.
        session = Session()
        filename = filepath.basename().decode("utf-8")
        fpath = os.path.join(dir_path, filename)

        log.debug("inotify: %s event on '%s'" %
                  (twisted.internet.inotify.humanReadableMask(mask), fpath))

        path, name = os.path.split(fpath)

        if mask & twisted.internet.inotify.IN_CREATE:
            if self.__isdir_event(mask)\
                    or self.__occured_on_dirlink(library, fpath):
                library.crawl_directory(path, name)
        elif mask & twisted.internet.inotify.IN_DELETE:
            if self.__isdir_event(mask)\
                    or self.__occured_on_dirlink(library, fpath):
                library.remove_directory(path, name)
            elif not self.__isdir_event(mask):
                library.remove_file(path, name)
        elif mask & twisted.internet.inotify.IN_MOVED_FROM:
            if not self.__isdir_event(mask):
                library.remove_file(path, name)
            else:
                library.remove_directory(path, name)
        elif mask & twisted.internet.inotify.IN_MOVED_TO:
            if not self.__isdir_event(mask):
                library.update_file(path, name)
            else:
                library.crawl_directory(path, name)
        elif mask & twisted.internet.inotify.IN_CLOSE_WRITE:
            library.update_file(path, name)

        session.commit()
        session.close()
Exemplo n.º 18
0
    def __init__(self, path):
        super(BaseLibrary, self).__init__()

        # get root path for this library
        path = os.path.abspath(path).rstrip("/")
        self.root_path = path
        # test library path
        if not os.path.isdir(self.root_path):
            msg = _("Unable to find '%s' folder in library") % self.root_path
            raise DeejaydError(msg)

        library = Session.query(Library) \
                         .filter(Library.name == self.TYPE) \
                         .one_or_none()
        if library is None:
            library = Library(name=self.TYPE, path=self.root_path)
            Session.add(library)
            Session.commit()
        self.library_id = library.id
        self.updating_state = {"id": 0, "running": False, "error": None}
        self.parser = self.PARSER(self)
        self.watcher = None
        self.load_state()
Exemplo n.º 19
0
    def __reload_list(self):
        log.msg(_("Start to reload icecast webradio source"))
        url = DeejaydConfig().get("webradio", "icecast_url")
        try:
            page_handle = urllib.request.urlopen(url, timeout=TIMEOUT)
            xml_page = page_handle.read()
        except Exception:
            raise DeejaydError(_("Unable to connect to icecast website"))

        # try to parse result
        try:
            root = ET.fromstring(xml_page)
        except ET.XMLSyntaxError:
            raise DeejaydError(_("Unable to parse icecast webradio list"))
        except Exception:
            raise DeejaydError(
                _("Unable to read result from icecast "
                  "webradio list"))
        finally:
            page_handle.close()

        DatabaseLock.acquire()
        session = Session()
        source = session.query(WebradioSource)\
                        .filter(WebradioSource.name == self.NAME)\
                        .one()
        # delete old entries from the database
        session.query(Webradio)\
               .filter(Webradio.source_id == source.id)\
               .delete(synchronize_session='fetch')
        session.query(WebradioCategory)\
               .filter(WebradioCategory.source_id == source.id)\
               .delete(synchronize_session='fetch')

        categories = {}
        webradios = {}
        for station in root:
            try:
                server_type = station.find("server_type").text
                listen_url = station.find("listen_url").text
                genres = station.find("genre").text
                name = station.find("server_name").text
            except TypeError:
                continue

            if server_type.startswith("audio") or \
                    (server_type == "application/ogg" and
                     not listen_url.endswith("ogv")):
                if name not in webradios:
                    genres = genres.split(" ")
                    webradios[name] = Webradio(source=source, name=name)
                    for genre in genres:
                        if len(genre) <= 2 or genre.startswith("."):
                            continue
                        genre = genre.capitalize()
                        if genre not in categories:
                            categories[genre] = WebradioCategory(name=genre,
                                                                 source=source)
                        webradios[name].categories.append(categories[genre])
                    session.add(webradios[name])
                webradios[name].entries.append(WebradioEntry(url=listen_url))
                log.debug('Added icecast webradio %s' % name)
        session.commit()
        Session.remove()
        DatabaseLock.release()

        log.msg(_("Finish to reload icecast webradio source"))
        return {
            "wb_count": len(webradios),
            "cat_count": len(categories),
        }