# Buggy code
def get_nick_id(self, nick, create=True):
    """Return the internal identifier for a given nick.

    This identifier is unique to a user, and shared across all of that
    user's aliases. If create is True, a new ID will be created if one does
    not already exist"""
    slug = nick.lower()
    nick_id = self.execute(
        "SELECT nick_id from nicknames where slug = ?", [slug]
    ).fetchone()
    if nick_id is None:
        if not create:
            raise ValueError("No ID exists for the given nick")
        with self.connect() as conn:
            cur = conn.cursor()
            cur.execute("INSERT INTO nick_ids VALUES (NULL)")
            nick_id = cur.execute("SELECT last_insert_rowid()").fetchone()[0]
            cur.execute(
                "INSERT INTO nicknames (nick_id, slug, canonical) VALUES (?, ?, ?)",
                [nick_id, slug, nick],
            )
        nick_id = self.execute(
            "SELECT nick_id from nicknames where slug = ?", [slug]
        ).fetchone()
    return nick_id[0]


# Traceback (OperationalError)
Traceback (most recent call last):
File "/home/TrollOP/willie/willie/bot.py", line 634, in call
exit_code = func(willie, trigger)
File "/home/TrollOP/willie/willie/modules/seen.py", line 50, in note
bot.db.set_nick_value(trigger.nick, 'seen_timestamp', time.time())
File "/home/TrollOP/willie/willie/db.py", line 150, in set_nick_value
nick_id = self.get_nick_id(nick)
File "/home/TrollOP/willie/willie/db.py", line 114, in get_nick_id
[slug]).fetchone()
File "/home/TrollOP/willie/willie/db.py", line 64, in execute
return cur.execute(*args, **kwargs)
OperationalError: database is locked

Traceback (most recent call last):
File "/home/TrollOP/willie/willie/bot.py", line 634, in call
exit_code = func(willie, trigger)
File "/home/TrollOP/willie/willie/modules/weather.py", line 129, in weather
woeid = bot.db.get_nick_value(trigger.nick, 'woeid')
File "/home/TrollOP/willie/willie/db.py", line 161, in get_nick_value
[nick.lower(), key]
File "/home/TrollOP/willie/willie/db.py", line 64, in execute
return cur.execute(*args, **kwargs)
OperationalError: database is locked

Traceback (most recent call last):
File "/home/TrollOP/willie/willie/bot.py", line 634, in call
exit_code = func(willie, trigger)
File "/home/TrollOP/willie/willie/modules/seen.py", line 50, in note
bot.db.set_nick_value(trigger.nick, 'seen_timestamp', time.time())
File "/home/TrollOP/willie/willie/db.py", line 152, in set_nick_value
[nick_id, key, value])
File "/home/TrollOP/willie/willie/db.py", line 64, in execute
return cur.execute(*args, **kwargs)
OperationalError: database is locked

# Fixed code
def get_nick_id(self, nick, create=True):
    """Return the internal identifier for a given nick.

    This identifier is unique to a user, and shared across all of that
    user's aliases. If create is True, a new ID will be created if one does
    not already exist"""
    session = self.ssession()
    slug = nick.lower()
    try:
        nickname = session.query(Nicknames).filter(Nicknames.slug == slug).one_or_none()

        if nickname is None:
            if not create:
                raise ValueError("No ID exists for the given nick")
            # Generate a new ID
            nick_id = NickIDs()
            session.add(nick_id)
            session.commit()

            # Create a new Nickname
            nickname = Nicknames(nick_id=nick_id.nick_id, slug=slug, canonical=nick)
            session.add(nickname)
            session.commit()
        return nickname.nick_id
    except SQLAlchemyError:
        session.rollback()
        raise
    finally:
        session.close()