Beispiel #1
0
def getTagTopArtists(tag, limit=50):
    myDB = db.DBConnection()
    results = myDB.select("SELECT ArtistID from artists")

    logger.info("Fetching top artists from Last.FM for tag: %s", tag)
    data = request_lastfm("tag.gettopartists", limit=limit, tag=tag)

    if data and "topartists" in data:
        artistlist = []
        artists = data["topartists"]["artist"]
        logger.debug("Fetched %d artists from Last.FM", len(artists))

        for artist in artists:
            try:
                artist_mbid = artist["mbid"]
            except KeyError:
                continue

            if not any(artist_mbid in x for x in results):
                artistlist.append(artist_mbid)

        from headphones import importer

        for artistid in artistlist:
            importer.addArtisttoDB(artistid)

        logger.debug("Added %d new artists from Last.FM", len(artistlist))
Beispiel #2
0
 def history(self):
     myDB = db.DBConnection()
     history = myDB.select(
         '''SELECT * from snatched order by DateAdded DESC''')
     return serve_template(templatename="history.html",
                           title="History",
                           history=history)
Beispiel #3
0
def findArtistbyAlbum(name):

    myDB = db.DBConnection()

    artist = myDB.action(
        'SELECT AlbumTitle from have WHERE ArtistName=? AND AlbumTitle IS NOT NULL ORDER BY RANDOM()',
        [name]).fetchone()

    if not artist:
        return False

    # Probably not neccessary but just want to double check
    if not artist['AlbumTitle']:
        return False

    term = '"' + artist['AlbumTitle'] + '" AND artist:"' + name + '"'

    results = None

    try:
        results = musicbrainzngs.search_release_groups(term).get(
            'release-group-list')
    except WebServiceError, e:
        logger.warn('Attempt to query MusicBrainz for %s failed (%s)' %
                    (name, str(e)))
        time.sleep(5)
Beispiel #4
0
 def unqueueAlbum(self, AlbumID, ArtistID):
     logger.info(u"Marking album: " + AlbumID + "as skipped...")
     myDB = db.DBConnection()
     controlValueDict = {'AlbumID': AlbumID}
     newValueDict = {'Status': 'Skipped'}
     myDB.upsert("albums", newValueDict, controlValueDict)
     raise cherrypy.HTTPRedirect("artistPage?ArtistID=%s" % ArtistID)
Beispiel #5
0
 def manageArtists(self):
     myDB = db.DBConnection()
     artists = myDB.select(
         'SELECT * from artists order by ArtistSortName COLLATE NOCASE')
     return serve_template(templatename="manageartists.html",
                           title="Manage Artists",
                           artists=artists)
Beispiel #6
0
	def getExtras(self, ArtistID):
		myDB = db.DBConnection()
		controlValueDict = {'ArtistID': ArtistID}
		newValueDict = {'IncludeExtras': 1}
		myDB.upsert("artists", newValueDict, controlValueDict)
		threading.Thread(target=importer.addArtisttoDB, args=[ArtistID, True]).start()
		raise cherrypy.HTTPRedirect("artistPage?ArtistID=%s" % ArtistID)
Beispiel #7
0
    def getExtras(self, ArtistID, newstyle=False, **kwargs):
        # if calling this function without the newstyle, they're using the old format
        # which doesn't separate extras, so we'll grab all of them
        #
        # If they are, we need to convert kwargs to string format
        if not newstyle:
            extras = "1,2,3,4,5,6,7,8"
        else:
            temp_extras_list = []
            # TODO: Put these extras as a global variable
            i = 1
            for extra in [
                    "single", "ep", "compilation", "soundtrack", "live",
                    "remix", "spokenword", "audiobook"
            ]:
                if extra in kwargs:
                    temp_extras_list.append(i)
                i += 1
            extras = ','.join(str(n) for n in temp_extras_list)

        myDB = db.DBConnection()
        controlValueDict = {'ArtistID': ArtistID}
        newValueDict = {'IncludeExtras': 1, 'Extras': extras}
        myDB.upsert("artists", newValueDict, controlValueDict)
        threading.Thread(target=importer.addArtisttoDB, args=[ArtistID,
                                                              True]).start()
        raise cherrypy.HTTPRedirect("artistPage?ArtistID=%s" % ArtistID)
Beispiel #8
0
def searchforalbum(albumid=None, new=False, lossless=False):
    
    if not albumid:

        myDB = db.DBConnection()
    
        results = myDB.select('SELECT AlbumID, Status from albums WHERE Status="Wanted" OR Status="Wanted Lossless"')
        new = True
         
        for result in results:
            foundNZB = "none"
            if (headphones.NZBMATRIX or headphones.NEWZNAB or headphones.NZBSORG or headphones.NEWZBIN) and (headphones.SAB_HOST or headphones.BLACKHOLE):
                if result['Status'] == "Wanted Lossless":
                    foundNZB = searchNZB(result['AlbumID'], new, losslessOnly=True)
                else:
                    foundNZB = searchNZB(result['AlbumID'], new)

            if (headphones.KAT or headphones.ISOHUNT or headphones.MININOVA or headphones.WAFFLES) and foundNZB == "none":
                if result['Status'] == "Wanted Lossless":
                    searchTorrent(result['AlbumID'], new, losslessOnly=True)
                else:
                    searchTorrent(result['AlbumID'], new)
            
    else:        
    
        foundNZB = "none"
        if (headphones.NZBMATRIX or headphones.NEWZNAB or headphones.NZBSORG or headphones.NEWZBIN) and (headphones.SAB_HOST or headphones.BLACKHOLE):
            foundNZB = searchNZB(albumid, new, lossless)

        if (headphones.KAT or headphones.ISOHUNT or headphones.MININOVA or headphones.WAFFLES) and foundNZB == "none":
            searchTorrent(albumid, new, lossless)
def checkTorrentFinished():
    """
    Remove Torrent + data if Post Processed and finished Seeding
    """

    logger.info("Checking if any torrents have finished seeding and can be removed")

    with postprocessor_lock:
        myDB = db.DBConnection()
        results = myDB.select('SELECT * from snatched WHERE Status="Seed_Processed"')

        for album in results:
            hash = album['FolderName']
            albumid = album['AlbumID']
            torrent_removed = False
            if headphones.CONFIG.TORRENT_DOWNLOADER == 1:
                torrent_removed = transmission.removeTorrent(hash, True)
            else:
                torrent_removed = utorrent.removeTorrent(hash, True)

            if torrent_removed:
                myDB.action('DELETE from snatched WHERE status = "Seed_Processed" and AlbumID=?',
                            [albumid])

    logger.info("Checking finished torrents completed")
def checkFolder():
    
    with postprocessor_lock:

        myDB = db.DBConnection()
        snatched = myDB.select('SELECT * from snatched WHERE Status="Snatched"')

        for album in snatched:
        
            if album['FolderName']:
                
                # Need to check for variations due to sab renaming. Ideally we'd check the sab config via api to 
                # figure out which options are checked, but oh well

                nzb_album_possibilities = [ album['FolderName'],
                                            sab_replace_dots(album['FolderName']),
                                            sab_replace_spaces(album['FolderName']),
                                            sab_replace_dots(sab_replace_spaces(album['FolderName']))
                                        ]

                torrent_album_path = os.path.join(headphones.DOWNLOAD_TORRENT_DIR, album['FolderName']).encode(headphones.SYS_ENCODING)

                for nzb_folder_name in nzb_album_possibilities:
                    
                    nzb_album_path = os.path.join(headphones.DOWNLOAD_DIR, nzb_folder_name).encode(headphones.SYS_ENCODING)

                    if os.path.exists(nzb_album_path):
                        logger.debug('Found %s in NZB download folder. Verifying....' % album['FolderName'])
                        verify(album['AlbumID'], nzb_album_path)

                if os.path.exists(torrent_album_path):
                    logger.debug('Found %s in torrent download folder. Verifying....' % album['FolderName'])
                    verify(album['AlbumID'], torrent_album_path)
Beispiel #11
0
def checkFolder():

    with postprocessor_lock:

        myDB = db.DBConnection()
        snatched = myDB.select(
            'SELECT * from snatched WHERE Status="Snatched"')

        for album in snatched:

            if album['FolderName']:

                nzb_album_path = os.path.join(headphones.DOWNLOAD_DIR,
                                              album['FolderName']).encode(
                                                  headphones.SYS_ENCODING)
                torrent_album_path = os.path.join(
                    headphones.DOWNLOAD_TORRENT_DIR,
                    album['FolderName']).encode(headphones.SYS_ENCODING)

                if os.path.exists(nzb_album_path):
                    logger.debug(
                        'Found %s in NZB download folder. Verifying....' %
                        album['FolderName'])
                    verify(album['AlbumID'], nzb_album_path)

                elif os.path.exists(torrent_album_path):
                    logger.debug(
                        'Found %s in torrent download folder. Verifying....' %
                        album['FolderName'])
                    verify(album['AlbumID'], torrent_album_path)
Beispiel #12
0
def findArtistbyAlbum(name):

    myDB = db.DBConnection()

    artist = myDB.action(
        'SELECT AlbumTitle from have WHERE ArtistName=? AND AlbumTitle IS NOT NULL ORDER BY RANDOM()',
        [name]).fetchone()

    if not artist:
        return False

    # Probably not neccessary but just want to double check
    if not artist['AlbumTitle']:
        return False

    term = '"' + artist['AlbumTitle'] + '" AND artist:"' + name + '"'

    f = ws.ReleaseGroupFilter(query=term, limit=1)
    results = None
    attempt = 0

    while attempt < 5:

        try:
            results = q.getReleaseGroups(f)
            break
        except WebServiceError, e:
            logger.warn(
                'Attempt to query MusicBrainz for %s failed: %s. Sleeping 5 seconds.'
                % (name, e))
            attempt += 1
            time.sleep(5)
Beispiel #13
0
def checkFolder():
    
    with postprocessor_lock:

        myDB = db.DBConnection()
        snatched = myDB.select('SELECT * from snatched WHERE Status="Snatched"')

        for album in snatched:
        
            if album['FolderName']:
                
                # We're now checking sab config options after sending to determine renaming - but we'll keep the
                # iterations in just in case we can't read the config for some reason

                nzb_album_possibilities = [ album['FolderName'],
                                            sab_replace_dots(album['FolderName']),
                                            sab_replace_spaces(album['FolderName']),
                                            sab_replace_spaces(sab_replace_dots(album['FolderName']))
                                        ]

                torrent_album_path = os.path.join(headphones.DOWNLOAD_TORRENT_DIR, album['FolderName']).encode(headphones.SYS_ENCODING)

                for nzb_folder_name in nzb_album_possibilities:
                    
                    nzb_album_path = os.path.join(headphones.DOWNLOAD_DIR, nzb_folder_name).encode(headphones.SYS_ENCODING)

                    if os.path.exists(nzb_album_path):
                        logger.debug('Found %s in NZB download folder. Verifying....' % album['FolderName'])
                        verify(album['AlbumID'], nzb_album_path, album['Kind'])

                if os.path.exists(torrent_album_path):
                    logger.debug('Found %s in torrent download folder. Verifying....' % album['FolderName'])
                    verify(album['AlbumID'], torrent_album_path, album['Kind'])
Beispiel #14
0
def finalize_update(artistid, artistname, errors=False):
    # Moving this little bit to it's own function so we can update have tracks & latest album when deleting extras

    myDB = db.DBConnection()

    latestalbum = myDB.action('SELECT AlbumTitle, ReleaseDate, AlbumID from albums WHERE ArtistID=? order by ReleaseDate DESC', [artistid]).fetchone()
    totaltracks = len(myDB.select('SELECT TrackTitle from tracks WHERE ArtistID=? AND AlbumID IN (SELECT AlbumID FROM albums WHERE Status != "Ignored")', [artistid]))
    #havetracks = len(myDB.select('SELECT TrackTitle from tracks WHERE ArtistID=? AND Location IS NOT NULL', [artistid])) + len(myDB.select('SELECT TrackTitle from have WHERE ArtistName like ?', [artist['artist_name']]))
    havetracks = len(myDB.select('SELECT TrackTitle from tracks WHERE ArtistID=? AND Location IS NOT NULL', [artistid])) + len(myDB.select('SELECT TrackTitle from have WHERE ArtistName like ? AND Matched = "Failed"', [artistname]))

    controlValueDict = {"ArtistID":     artistid}

    if latestalbum:
        newValueDict = {"Status":           "Active",
                        "LatestAlbum":      latestalbum['AlbumTitle'],
                        "ReleaseDate":      latestalbum['ReleaseDate'],
                        "AlbumID":          latestalbum['AlbumID'],
                        "TotalTracks":      totaltracks,
                        "HaveTracks":       havetracks}
    else:
        newValueDict = {"Status":           "Active",
                        "TotalTracks":      totaltracks,
                        "HaveTracks":       havetracks}

    if not errors:
        newValueDict['LastUpdated'] = helpers.now()

    myDB.upsert("artists", newValueDict, controlValueDict)
Beispiel #15
0
	def artistPage(self, ArtistID):
		myDB = db.DBConnection()
		artist = myDB.action('SELECT * FROM artists WHERE ArtistID=?', [ArtistID]).fetchone()
		albums = myDB.select('SELECT * from albums WHERE ArtistID=? order by ReleaseDate DESC', [ArtistID])
		if artist is None:
			raise cherrypy.HTTPRedirect("home")
		return serve_template(templatename="artist.html", title=artist['ArtistName'], artist=artist, albums=albums)
Beispiel #16
0
def updateFormat():
    myDB = db.DBConnection()
    tracks = myDB.select(
        'SELECT * from tracks WHERE Location IS NOT NULL and Format IS NULL')
    if len(tracks) > 0:
        logger.info('Finding media format for %s files' % len(tracks))
        for track in tracks:
            try:
                f = MediaFile(track['Location'])
            except Exception as e:
                logger.info("Exception from MediaFile for: " +
                            track['Location'] + " : " + str(e))
                continue
            controlValueDict = {"TrackID": track['TrackID']}
            newValueDict = {"Format": f.format}
            myDB.upsert("tracks", newValueDict, controlValueDict)
        logger.info('Finished finding media format for %s files' % len(tracks))
    havetracks = myDB.select(
        'SELECT * from have WHERE Location IS NOT NULL and Format IS NULL')
    if len(havetracks) > 0:
        logger.info('Finding media format for %s files' % len(havetracks))
        for track in havetracks:
            try:
                f = MediaFile(track['Location'])
            except Exception as e:
                logger.info("Exception from MediaFile for: " +
                            track['Location'] + " : " + str(e))
                continue
            controlValueDict = {"TrackID": track['TrackID']}
            newValueDict = {"Format": f.format}
            myDB.upsert("have", newValueDict, controlValueDict)
        logger.info('Finished finding media format for %s files' %
                    len(havetracks))
Beispiel #17
0
	def albumPage(self, AlbumID):
		myDB = db.DBConnection()
		album = myDB.action('SELECT * from albums WHERE AlbumID=?', [AlbumID]).fetchone()
		tracks = myDB.select('SELECT * from tracks WHERE AlbumID=?', [AlbumID])
		description = myDB.action('SELECT * from descriptions WHERE ReleaseGroupID=?', [AlbumID]).fetchone()
		title = album['ArtistName'] + ' - ' + album['AlbumTitle']
		return serve_template(templatename="album.html", title=title, album=album, tracks=tracks, description=description)
Beispiel #18
0
def artistlist_to_mbids(artistlist, forced=False):

    for artist in artistlist:

        if not artist and not (artist == ' '):
            continue

        results = mb.findArtist(artist, limit=1)

        if not results:
            logger.info('No results found for: %s' % artist)
            continue

        try:
            artistid = results[0]['id']

        except IndexError:
            logger.info('MusicBrainz query turned up no matches for: %s' %
                        artist)
            continue

        # Check if it's blacklisted/various artists (only check if it's not forced, e.g. through library scan auto-add.)
        # Forced example = Adding an artist from Manage New Artists
        myDB = db.DBConnection()

        if not forced:
            bl_artist = myDB.action('SELECT * FROM blacklist WHERE ArtistID=?',
                                    [artistid]).fetchone()
            if bl_artist or artistid in blacklisted_special_artists:
                logger.info(
                    "Artist ID for '%s' is either blacklisted or Various Artists. To add artist, you must do it manually (Artist ID: %s)"
                    % (artist, artistid))
                continue

        # Add to database if it doesn't exist
        if not is_exists(artistid):
            addArtisttoDB(artistid)

        # Just update the tracks if it does
        else:
            havetracks = len(
                myDB.select('SELECT TrackTitle from tracks WHERE ArtistID=?', [
                    artistid
                ])) + len(
                    myDB.select(
                        'SELECT TrackTitle from have WHERE ArtistName like ?',
                        [artist]))
            myDB.action('UPDATE artists SET HaveTracks=? WHERE ArtistID=?',
                        [havetracks, artistid])

        # Delete it from the New Artists if the request came from there
        if forced:
            myDB.action('DELETE from newartists WHERE ArtistName=?', [artist])

    # Update the similar artist tag cloud:
    logger.info('Updating artist information from Last.fm')
    try:
        lastfm.getSimilar()
    except Exception, e:
        logger.warn('Failed to update arist information from Last.fm: %s' % e)
Beispiel #19
0
 def extras(self):
     myDB = db.DBConnection()
     cloudlist = myDB.select('SELECT * from lastfmcloud')
     return serve_template(templatename="extras.html",
                           title="Extras",
                           cloudlist=cloudlist)
     return page
Beispiel #20
0
def getTagTopArtists(tag, limit=50):
    myDB = db.DBConnection()
    results = myDB.select('SELECT ArtistID from artists')

    url = 'http://ws.audioscrobbler.com/2.0/?method=tag.gettopartists&limit=%s&tag=%s&api_key=%s' % (
        limit, tag, api_key)
    data = urllib2.urlopen(url, timeout=20).read()

    try:
        d = minidom.parseString(data)
    except:
        logger.error("Could not parse artist list from last.fm data")
        return

    artists = d.getElementsByTagName("artist")

    artistlist = []

    for artist in artists:
        mbidnode = artist.getElementsByTagName("mbid")[0].childNodes

        for node in mbidnode:
            artist_mbid = node.data

        try:
            if not any(artist_mbid in x for x in results):
                artistlist.append(artist_mbid)
        except:
            continue

    from headphones import importer

    for artistid in artistlist:
        importer.addArtisttoDB(artistid)
Beispiel #21
0
 def resumeArtist(self, ArtistID):
     logger.info(u"Resuming artist: " + ArtistID)
     myDB = db.DBConnection()
     controlValueDict = {'ArtistID': ArtistID}
     newValueDict = {'Status': 'Active'}
     myDB.upsert("artists", newValueDict, controlValueDict)
     raise cherrypy.HTTPRedirect("artistPage?ArtistID=%s" % ArtistID)
Beispiel #22
0
def addReleaseById(rid):
    
    myDB = db.DBConnection()

    rgid = None
    artistid = None
    release_dict = None
    results = myDB.select("SELECT albums.ArtistID, releases.ReleaseGroupID from releases, albums WHERE releases.ReleaseID=? and releases.ReleaseGroupID=albums.AlbumID LIMIT 1", [rid])
    for result in results:
        rgid = result['ReleaseGroupID']
        artistid = result['ArtistID']
        logger.debug("Found a cached releaseid : releasegroupid relationship: " + rid + " : " + rgid)
    if not rgid:
        #didn't find it in the cache, get the information from MB
        logger.debug("Didn't find releaseID " + rid + " in the cache. Looking up its ReleaseGroupID")
        try:
            release_dict = mb.getRelease(rid)
        except Exception, e:
            logger.info('Unable to get release information for Release: ' + str(rid) + " " + str(e))
            return
        if not release_dict:
            logger.info('Unable to get release information for Release: ' + str(rid) + " no dict")
            return
        
        rgid = release_dict['rgid']
        artistid = release_dict['artist_id']
Beispiel #23
0
 def manage(self):
     myDB = db.DBConnection()
     emptyArtists = myDB.select(
         "SELECT * FROM artists WHERE LatestAlbum IS NULL")
     return serve_template(templatename="manage.html",
                           title="Manage",
                           emptyArtists=emptyArtists)
Beispiel #24
0
def getArtists():
    myDB = db.DBConnection()
    results = myDB.select("SELECT ArtistID from artists")

    if not headphones.CONFIG.LASTFM_USERNAME:
        logger.warn("Last.FM username not set, not importing artists.")
        return

    logger.info("Fetching artists from Last.FM for username: %s",
                headphones.CONFIG.LASTFM_USERNAME)
    data = request_lastfm("library.getartists",
                          limit=10000,
                          user=headphones.CONFIG.LASTFM_USERNAME)

    if data and "artists" in data:
        artistlist = []
        artists = data["artists"]["artist"]
        logger.debug("Fetched %d artists from Last.FM", len(artists))

        for artist in artists:
            artist_mbid = artist["mbid"]

            if not any(artist_mbid in x for x in results):
                artistlist.append(artist_mbid)

        from headphones import importer

        for artistid in artistlist:
            importer.addArtisttoDB(artistid)

        logger.info("Imported %d new artists from Last.FM", len(artistlist))
Beispiel #25
0
 def markArtists(self, action=None, **args):
     myDB = db.DBConnection()
     artistsToAdd = []
     for ArtistID in args:
         if action == 'delete':
             myDB.action('DELETE from artists WHERE ArtistID=?', [ArtistID])
             myDB.action('DELETE from albums WHERE ArtistID=?', [ArtistID])
             myDB.action('DELETE from tracks WHERE ArtistID=?', [ArtistID])
             myDB.action('INSERT OR REPLACE into blacklist VALUES (?)',
                         [ArtistID])
         elif action == 'pause':
             controlValueDict = {'ArtistID': ArtistID}
             newValueDict = {'Status': 'Paused'}
             myDB.upsert("artists", newValueDict, controlValueDict)
         elif action == 'resume':
             controlValueDict = {'ArtistID': ArtistID}
             newValueDict = {'Status': 'Active'}
             myDB.upsert("artists", newValueDict, controlValueDict)
         else:
             artistsToAdd.append(ArtistID)
     if len(artistsToAdd) > 0:
         logger.debug("Refreshing artists: %s" % artistsToAdd)
         threading.Thread(target=importer.addArtistIDListToDB,
                          args=[artistsToAdd]).start()
     raise cherrypy.HTTPRedirect("home")
Beispiel #26
0
    def _queueAlbum(self, **kwargs):

        if 'id' not in kwargs:
            self.data = 'Missing parameter: id'
            return
        else:
            self.id = kwargs['id']

        if 'new' in kwargs:
            new = kwargs['new']
        else:
            new = False

        if 'lossless' in kwargs:
            lossless = kwargs['lossless']
        else:
            lossless = False

        myDB = db.DBConnection()
        controlValueDict = {'AlbumID': self.id}
        if lossless:
            newValueDict = {'Status': 'Wanted Lossless'}
        else:
            newValueDict = {'Status': 'Wanted'}
        myDB.upsert("albums", newValueDict, controlValueDict)
        searcher.searchforalbum(self.id, new)
Beispiel #27
0
 def home(self):
     myDB = db.DBConnection()
     artists = myDB.select(
         'SELECT * from artists order by ArtistSortName COLLATE NOCASE')
     return serve_template(templatename="index.html",
                           title="Home",
                           artists=artists)
Beispiel #28
0
	def deleteArtist(self, ArtistID):
		logger.info(u"Deleting all traces of artist: " + ArtistID)
		myDB = db.DBConnection()
		myDB.action('DELETE from artists WHERE ArtistID=?', [ArtistID])
		myDB.action('DELETE from albums WHERE ArtistID=?', [ArtistID])
		myDB.action('DELETE from tracks WHERE ArtistID=?', [ArtistID])
		raise cherrypy.HTTPRedirect("home")
Beispiel #29
0
    def get_info_from_cache(self, ArtistID=None, AlbumID=None):

        self.query_type = 'info'
        myDB = db.DBConnection()

        if ArtistID:
            self.id = ArtistID
            self.id_type = 'artist'
            db_info = myDB.action(
                'SELECT Summary, Content, LastUpdated FROM descriptions WHERE ArtistID=?',
                [self.id]).fetchone()
        else:
            self.id = AlbumID
            self.id_type = 'album'
            db_info = myDB.action(
                'SELECT Summary, Content, LastUpdated FROM descriptions WHERE ReleaseGroupID=?',
                [self.id]).fetchone()

        if not db_info or not db_info['LastUpdated'] or not self._is_current(
                date=db_info['LastUpdated']):

            self._update_cache()
            info_dict = {
                'Summary': self.info_summary,
                'Content': self.info_content
            }
            return info_dict

        else:
            info_dict = {
                'Summary': db_info['Summary'],
                'Content': db_info['Content']
            }
            return info_dict
Beispiel #30
0
 def editSearchTerm(self, AlbumID, SearchTerm):
     logger.info(u"Updating search term for albumid: " + AlbumID)
     myDB = db.DBConnection()
     controlValueDict = {'AlbumID': AlbumID}
     newValueDict = {'SearchTerm': SearchTerm}
     myDB.upsert("albums", newValueDict, controlValueDict)
     raise cherrypy.HTTPRedirect("albumPage?AlbumID=%s" % AlbumID)