Ejemplo n.º 1
0
def get_car_prices(car_df):
    """
    Crawls prices for the recommended cars and the user's car
    from kbb and adds them as columns to the inputted dataframe.
    Tries different options for model names to find a match and asks
    the user for an estimation if the price for their old car is
    not found.
    
    Parameters:
        car_df (pd.DataFrame): dataframe of cars to be recommended
    
    Returns:
        car_df (pd.DataFrame): dataframe of cars to be recommended
            with the added price and difference columns
        old_car_price (float): price of the user's current car
    """
    car_df["price"] = np.nan

    pm = urllib3.PoolManager(cert_reqs='CERT_REQUIRED',
                             ca_certs=certifi.where())

    old_car_price = None
    car_df = car_df.reset_index()
    car_df.loc[:, "model"] = car_df.loc[:, "model"].str.replace("/", " ")

    for i, row in car_df.iterrows():
        make, possible_models, year = get_info_for_price(row)
        if year < 1992 and i != len(car_df) - 1:
            continue
        for _, model in enumerate(possible_models):
            myurl = f"https://www.kbb.com/{make}/{model}/{year}/"
            html = pm.urlopen(url=myurl, method="GET").data
            soup = bs4.BeautifulSoup(html, features="html.parser")
            title = soup.find_all("title")[0].text
            if (("Find Your Perfect Car" not in title)
                    and ("Kelley Blue Book | Error" not in title)):
                break
        if (("Find Your Perfect Car" in title)
                or ("Kelley Blue Book | Error" in title)
                or (str(year) not in title)):
            continue
        price_text = soup.find_all("script", attrs={"data-rh":
                                                    "true"})[-1].text
        m = re.findall('"price":"([0-9]+)"', price_text)[0]
        if i == len(car_df) - 1:
            old_car_price = m
        car_df.loc[i, "price"] = float(m)

    old_car_price = q.text(
        'No associated price could be found for your car.'
        '\n   What do you believe your car is worth?\n   ',
        validate=lambda text: txt_validator(text),
        style=Style(S_CONFIG + [('qmark', 'fg:#CF5050')]),
        qmark='\n❗').skip_if(old_car_price is not None, old_car_price).ask()
    car_df["difference"] = (float(old_car_price) -
                            car_df.price[car_df.price.notna()])
    car_df = car_df.drop(car_df.tail(1).index)
    return car_df, old_car_price
Ejemplo n.º 2
0
def get_miles():
    """
    Asks user for estimation of their current weekly miles.
    Used to calculate their emission.

    Returns:
        float: user's estimated weekly milage
    """
    use_miles = q.text('Estimation for weekly miles driven?\n   ',
                       validate=lambda text: txt_validator(text),
                       style=Style(S_CONFIG),
                       qmark='\n⯁ ').ask()
    return float(use_miles)
Ejemplo n.º 3
0
def rank_pref():
    """
    Ranks vehicle attributes that user cares most about from their
    current car. Uses this information to more accurately recommend
    a new vehicle.

    Returns:
        lst: elements are arranged in order of priority
    """
    CHOICES = [
        'Make', 'Year', 'Transmission', 'Vehicle Class', 'Fuel Type',
        'Passenger capacity', 'Luggage Capacity', 'Stop Ranking'
    ]
    DICT_MAP = {
        'Make': 'make',
        'Year': 'year',
        'Transmission': 'trany',
        'Vehicle Class': 'VClass',
        'Fuel Type': 'fuelType',
        'Luggage Capacity': 'luggage_volume'
    }
    q.print(
        'We will now ask you to rank which attributes you like most '
        'about your current vehicle.\nThese choices will be taken into '
        'consideration for car recommendation.\nYou may rank until you '
        "feel you have no more preferences or until you've exhausted all "
        'options.',
        style=S_CONFIG[1][1])

    i = 1
    pref = ''
    rank_order = []
    while len(CHOICES) > 2:
        pref = q.select('Choose preference: ',
                        choices=CHOICES,
                        style=Style(S_CONFIG),
                        qmark='\n' + str(i)).ask()
        if pref == 'Stop Ranking':
            break
        CHOICES.remove(pref)
        rank_order.append(pref)
        i += 1
    if len(CHOICES) == 2:
        rank_order.append(CHOICES[0])
    # Rename items in rank list to the less human readable col names
    return list((pd.Series(rank_order, dtype='object')).map(DICT_MAP))
Ejemplo n.º 4
0
def unique_helper(c, col, col_desc, base_param, prev=[]):
    """
    Refines id search by checking if transmission, cylinder, or drive
    data is enough to uniquely identify a given car.

    Parameters:
        c (obj): cursor for current connection to database
        col (str): column we will query for uniqueness
        col_desc (str): modifies question string to best fit
            current query
        base_param (tup): make, model, year used as filters for
            query. These parameters are built upon as each
            successive question provides new information
        prev (lst): contains tuples of form
            (prev col queried, prev unique_helper result)
            needed so that later calls to this function may
            use new information to refine its query
    
    Returns:
        tup:ans (str) - the feature selected by the user that matches
            their current car. Can also be None if there is only one
            possible choice of that feature given the query
            restrictions or if user is unsure
            cond (str) - (used only the last time the function is
            called) saves WHERE clause to be used outside the function
    """
    add_cond, param_tup = '', ()
    prev = [tup for tup in prev if tup[1]]
    if prev:
        cond_tup, param_tup = zip(*prev)
        for cond in cond_tup:
            add_cond += f' AND {cond} = ?'
    uniq_query = f'SELECT {col} FROM vehicles {WHERE_CMD} {add_cond}'
    uniq_results = c.execute(uniq_query, base_param + param_tup).fetchall()
    uniq_results = {str(tup[0]) for tup in uniq_results}
    uniq = len(uniq_results) == 1
    ans = q.select(f"Which matches your car's {col_desc}?\n   ",
                   choices=sorted(uniq_results) + ['Not Sure'],
                   style=Style(S_CONFIG),
                   qmark='\n⯁ ').skip_if(uniq).ask()
    if ans == 'Not Sure':
        ans = None
    return ans, add_cond
Ejemplo n.º 5
0
import os
import sys
from posixpath import expanduser
import subprocess
import argparse
from pathlib import Path
from colored import fg, attr
import logging

FORMAT = f"%(filename)s: {attr('bold')}%(levelname)s {fg(3)+attr('bold')}%(message)s{attr('reset')} line: %(lineno)s, %(relativeCreated)dms"
logging.basicConfig(format=FORMAT, level=logging.DEBUG)

logging.disable(logging.WARNING)

data_path = os.path.join(Path.home(), ".local/share/trening.json")
style = Style(questionary_style)


class Trening(object):

    def __init__(self) -> None:
        self.data_path = data_path
        self.load_conf()

    def load_conf(self) -> None:
        with open(self.data_path) as f:
            self.config = json.load(f)

        self.determine_exercise()
        self.cycle_rms = self.config[self.current_cycle + "_RMs"]
        self.one_rm = self.config["exercises"][self.current_exercise]["1RM"]
Ejemplo n.º 6
0
# Item prefix to identify selected items in a checkbox list
INDICATOR_SELECTED = "●"

# Item prefix to identify unselected items in a checkbox list
INDICATOR_UNSELECTED = "○"

# Prefix displayed in front of questions
DEFAULT_QUESTION_PREFIX = "?"

# Message shown when a user aborts a question prompt using CTRL-C
DEFAULT_KBI_MESSAGE = "Cancelled by user"

# Default text shown when the input is invalid
INVALID_INPUT = "Invalid input"

# Default message style
DEFAULT_STYLE = Style(
    [
        ("qmark", "fg:#5f819d"),  # token in front of the question
        ("question", "bold"),  # question text
        ("answer", "fg:#FF9D00 bold"),  # submitted answer text behind the question
        ("pointer", ""),  # pointer used in select and checkbox prompts
        ("selected", ""),  # style for a selected item of a checkbox
        ("separator", ""),  # separator in lists
        ("instruction", ""),  # user instructions for select, rawselect, checkbox
        ("text", ""),  # any other text
        ("instruction", ""),  # user instructions for select, rawselect, checkbox
    ]
)
Ejemplo n.º 7
0
def get_id(conn):
    """
    Extracts unique id from database by narrowing down candidates based
    on user provided information. Some cars continue to have variants
    even after all questions have been asked. For those that do, the
    first id fetched by the final query result is the one we will use.

    Parameters:
        conn (obj): connection to sqlite database we will be querying

    Returns:
        int: identifier for user's current car, used as a means to
            access other information related to their vehicle for
            future functions
    """
    c = conn.cursor()
    make_query = 'SELECT DISTINCT make FROM vehicles'
    make_results = c.execute(make_query).fetchall()
    make_results = sorted({tup[0] for tup in make_results})
    make_ans = q.autocomplete(
        "What is your car's make?\n   ",
        choices=make_results,
        validate=(lambda text: autoc_validator(text, c, 'make')),
        style=Style(S_CONFIG),
        qmark='⯁ ').ask()

    m_y_query = ('SELECT DISTINCT model, year ' 'FROM vehicles WHERE make = ?')
    m_y_results = set(c.execute(m_y_query, (make_ans, )).fetchall())
    m_y_results = sorted(m_y_results, key=lambda tup: (tup[0], -tup[1]))
    m_y_results = [tup[0] + ' ' + str(tup[1]) for tup in m_y_results]
    m_y_ans = q.autocomplete(
        'What about model and year?\n   ',
        choices=m_y_results,
        validate=(lambda text: autoc_validator(text, c, 'm_y')),
        style=Style(S_CONFIG),
        qmark='\n⯁ ').ask()
    model, _, year = m_y_ans.rpartition(' ')

    base_tup = (make_ans, model, int(year))
    id_query = f'SELECT id FROM vehicles {WHERE_CMD}'
    uniq_results = c.execute(id_query, base_tup).fetchall()
    uniq_results = [tup[0] for tup in uniq_results]
    id_ = uniq_results[0]
    uniq = len(uniq_results) == 1
    c_msg = ('Your particular car has some variants, would you like to be '
             'more specific?\n   You may be prompted to choose transmission, '
             'number of cylinders, or drive type.\n   Recommended only if '
             'you are comfortable with these more advanced options.\n   '
             '(Skipping defaults to No.)\n   ')
    advanced = q.confirm(c_msg,
                         default=False,
                         style=Style(S_CONFIG + [('qmark', 'fg:#CF5050')]),
                         qmark='\n❗').skip_if(uniq).ask()

    if advanced:
        t_ans, _ = unique_helper(c, 'trany', 'transmission', base_tup)
        c_ans, _ = unique_helper(c, 'cylinders', 'number of cylinders',
                                 base_tup, [('trany', t_ans)])
        d_ans, cond = unique_helper(c, 'drive', 'drive type', base_tup,
                                    [('trany', t_ans), ('cylinders', c_ans)])
        if d_ans:
            cond += ' AND drive = ?'
        add_tup = tuple(val for val in (t_ans, c_ans, d_ans) if val)
        id_query = 'SELECT id FROM vehicles ' + WHERE_CMD + cond
        id_ = c.execute(id_query, base_tup + add_tup).fetchone()[0]
    c.close()
    return id_
Ejemplo n.º 8
0
# User interface
custom_style_fancy = Style(
    [
        ("qmark", "fg:#673ab7 bold"),  # token in front of the question
        ("question", "bold"),  # question text
        (
            "answer",
            "fg:#f44336 bold",
        ),  # submitted answer text behind the question
        (
            "pointer",
            "fg:#673ab7 bold",
        ),  # pointer used in select and checkbox prompts
        (
            "highlighted",
            "fg:#673ab7 bold",
        ),  # pointed-at choice in select and checkbox prompts
        ("selected", "fg:#cc5454"),  # style for a selected item of a checkbox
        ("separator", "fg:#cc5454"),  # separator in lists
        (
            "instruction",
            "",
        ),  # user instructions for select, rawselect, checkbox
        ("text", ""),  # plain text
        (
            "disabled",
            "fg:#858585 italic",
        ),  # disabled choices for select and checkbox prompts
    ],
)
# Summary
Ejemplo n.º 9
0
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.

from questionary import prompt, print
from CryptoLibrary.utils import CryptoUtility
from questionary import Style

custom_style_fancy = Style([
    ('qmark', '#fac731 bold'),
    ('question', 'bold'),
    ('answer', '#06c8ff bold italic'),
    ('pointer', '#673ab7 bold'),
    ('highlighted', '#34AC5E bold'),
    ('selected', '#0abf5b'),
    ('separator', '#cc5454'),
    ('instruction', ''),
    ('text', ''),
    ('disabled', '#858585 italic'),
])

__version__ = '0.0.3'


class Encrypter(object):
    def main(self):
        self.main_menu()

    def main_menu(self):
        questions = [{
Ejemplo n.º 10
0
CUSTOM_STYLE = Style(
    [
        ("qmark", "ansibrightyellow bold"),  # token in front of the question
        ("question", "ansiwhite bold"),  # question text
        (
            "answer",
            "ansibrightmagenta bold",
        ),  # submitted answer text behind the question
        (
            "pointer",
            "ansibrightblue bold",
        ),  # pointer used in select and checkbox prompts
        (
            "highlighted",
            "ansibrightblack bold",
        ),  # pointed-at choice in select and checkbox prompts
        (
            "selected",
            "ansibrightblack",
        ),  # style for a selected item of a checkbox
        ("separator", "ansibrightmagenta"),  # separator in lists
        (
            "instruction",
            "",
        ),  # user instructions for select, rawselect, checkbox
        ("text", ""),  # plain text
        (
            "disabled",
            "ansibrightblack italic",
        ),  # disabled choices for select and checkbox prompts
    ]
)
Ejemplo n.º 11
0
from questionary import Style

custom_style_fancy = Style([
    ("separator", "fg:#cc5454"),
    ("qmark", "fg:#673ab7 bold"),
    ("question", ""),
    ("selected", "fg:#cc5454"),
    ("pointer", "fg:#673ab7 bold"),
    ("highlighted", "fg:#673ab7 bold"),
    ("answer", "fg:#f44336 bold"),
    ("text", "fg:#FBE9E7"),
    ("disabled", "fg:#858585 italic"),
])

custom_style_dope = Style([
    ("separator", "fg:#6C6C6C"),
    ("qmark", "fg:#FF9D00 bold"),
    ("question", ""),
    ("selected", "fg:#5F819D"),
    ("pointer", "fg:#FF9D00 bold"),
    ("answer", "fg:#5F819D bold"),
])

custom_style_genius = Style([
    ("qmark", "fg:#E91E63 bold"),
    ("question", ""),
    ("selected", "fg:#673AB7 bold"),
    ("answer", "fg:#2196f3 bold"),
])