def index(): """List all listings tags. @return: HTML with the listing tags index. @rtype: str """ config = tiny_classified.get_config() tags = services.listing_service.index_tags() categories = services.listing_service.collect_index_dict(tags, home_only=True) url_base = tiny_classified.get_config()["LISTING_URL_BASE"] html_categories = [render_html_category(url_base, cat, subcats) for cat, subcats in categories.iteritems()] temp_vals = tiny_classified.render_common_template_vals() temp_vals.update(temp_vals_extra) parent_template = config.get("PARENT_TEMPLATE", "tinyclassified_base.html") return flask.render_template( "public/public_index_chrome.html", base_url=config["BASE_URL"], parent_template=parent_template, html_categories=html_categories, **temp_vals )
def test_send_only_plain(self): test_service = TestEmailService() self.mox.StubOutWithMock(email_service, 'get_service_client') email_service.get_service_client( tiny_classified.get_config()['EMAIL_USERNAME'], tiny_classified.get_config()['EMAIL_PASSWORD'], tiny_classified.get_config()['EMAIL_USE_SECURE'], ).AndReturn(test_service) self.mox.ReplayAll() email_service.send( ['*****@*****.**'], 'subject', '**plain_body**' ) message = test_service.web.message mesg_dict = message.__dict__ self.assertEqual( mesg_dict['from_email'], tiny_classified.get_config()['EMAIL_FROM_ADDR'] ) self.assertEqual(mesg_dict['to'], ['*****@*****.**']) self.assertEqual(mesg_dict['subject'], 'subject') self.assertEqual(mesg_dict['text'], '**plain_body**') self.assertEqual(mesg_dict['html'], '<p><strong>plain_body</strong></p>')
def index_listings_by_slug_programmatic(slug, parent_template, temp_vals, home): listings = services.listing_service.list_by_slug(slug) slug_split = slug.split("/") category = slug_split[0] config = tiny_classified.get_config() if listings.count() == 0: return None listing = listings[0] is_qualified = services.listing_service.check_is_qualified(listing, slug) about = listing.get("about", None) if about: about = markdown.markdown(about) if listings.count() == 1 and is_qualified: return flask.render_template( "public/listing_chrome.html", base_url=config["BASE_URL"], parent_template=parent_template, listing=listing, category=category, about=about, listing_url_base=tiny_classified.get_config()["LISTING_URL_BASE"], admin=util.check_admin_requirement(True), **temp_vals ) else: tags = listings.distinct("tags") tags = services.listing_service.collect_index_dict(tags, home_only=home) if len(slug_split) > 1: subcategories = [] selected_subcategory = {"name": slug_split[1]} else: subcategories = tags[category] selected_subcategory = None url_base = config["LISTING_URL_BASE"] listings = list(listings) featured_listings = sorted(filter(lambda x: x.get("featured", False), listings), key=lambda x: x["name"]) prep = util.prepare_subcategory return flask.render_template( "public/category_chrome.html", base_url=config["BASE_URL"], parent_template=parent_template, category=category, listings=listings, featured_listings=featured_listings, subcategories=[prep(url_base, category, x) for x in subcategories], selected_subcategory=selected_subcategory, listing_url_base=url_base, **temp_vals )
def get_database(self): """Get the database for the application. @return: Database point provided by the native pymongo.MongoClient @rtype: pymongo.database """ app_config = tiny_classified.get_config() return self.client[app_config["MONGO_DATABASE_NAME"]]
def __init__(self): """Create a new database adapater around the database engine. @param client: The native database wrapper to adapt. @type client: flask.ext.pymongo.PyMongo """ app_config = tiny_classified.get_config() self.client = pymongo.mongo_client.MongoClient(app_config["MONGO_URI"])
def confirm_delete(): config = tiny_classified.get_config() temp_vals = tiny_classified.render_common_template_vals() temp_vals.update(temp_vals_extra) parent_template = config.get("PARENT_TEMPLATE", "tinyclassified_base.html") return flask.render_template( "public/deleted_confirmation.html", base_url=config["BASE_URL"], parent_template=parent_template, **temp_vals )
def forgot_password(): """Render the forgot password view with forgot password form. @return: The HTML forgot password view. @rtype: str """ config = tiny_classified.get_config() parent_template = config.get( 'PARENT_TEMPLATE', 'tinyclassified_base.html' ) return flask.render_template( 'login/forgot_password.html', base_url=config['BASE_URL'], parent_template=parent_template )
def index_tags_as_html(): """List all unique listings tags formatted as an HTML document. @return: List all unique listings tags formatted as an HTML document. @rtype: str """ tags = index_tags() categories = collect_index_dict(tags) template = None with open(INDEX_TEMPLATE_PATH) as f: template = jinja2.Template(f.read()) return template.render({ 'categories': categories, 'listing_url_base': tiny_classified.get_config()['LISTING_URL_BASE'] })
def collect_index_dict(taglists, home_only=True): """Collect the unique categories and subcategories into a dict. Compresses lists of listing tags into an intersection in the form of a dict. Unique categories are the keys of the resultant dict, which have values of lists of listing tag subcategories. Example input: taglists = [ {'altcat': ['altsubcat1', 'altsubcat2']}], {'altcat': ['altsubcat2', 'altsubcat3']}, {'cat': ['subcat2', 'subcat3']} ] example output: { 'altcat': ['altsubcat1', 'altsubcat2', 'altsubcat3'], 'cat': ['subcat2', 'subcat3'] } @param taglists: The lists of listings tags to collect. @type taglists: iterable over dict @return: Dict which has unique categories as the keys and lists of listing tag subcategories as values. @rtype: dict """ categories = {} for tags in taglists: for category, subcategories in tags.iteritems(): if categories.get(category, None) == None: categories[category] = [] for subcat in subcategories: if not subcat in categories[category]: categories[category].append(subcat) if home_only: to_ignore = tiny_classified.get_config()['NO_FRONT_PAGE_CATEGORIES'] categories = dict(filter( lambda (key, val): key not in to_ignore, categories.iteritems() )) return categories
def index_listings_by_slug(slug): """List all listings of a given slug. @param slug: The slug for which to list listings. @type slug: str @return: HTML with the listings belonging the the given slug. @rtype: str """ config = tiny_classified.get_config() temp_vals = tiny_classified.render_common_template_vals("resources/" + slug) temp_vals.update(temp_vals_extra) parent_template = config.get("PARENT_TEMPLATE", "tinyclassified_base.html") result = index_listings_by_slug_programmatic(slug, parent_template, temp_vals, True) if not result: flask.abort(404) return result
def show_user_ui(): """Render the chrome (UI constructs) for user / author controls. @return: Rendered HTML template with the author control interface. @rtype: str """ config = tiny_classified.get_config() temp_vals = tiny_classified.render_common_template_vals() parent_template = config.get( 'PARENT_TEMPLATE', 'tinyclassified_base.html' ) listing_view_templates = flask.render_template( 'author/listing_view.html', parent_template=parent_template, base_url=config['BASE_URL'] ) contacts_view_templates = flask.render_template( 'author/contacts_view.html', parent_template=parent_template, base_url=config['BASE_URL'] ) listing_about_templates = flask.render_template( 'author/listing_about.html', parent_template=parent_template, base_url=config['BASE_URL'] ) return flask.render_template( 'author/author_chrome.html', parent_template=parent_template, listing_view_templates=listing_view_templates, contacts_view_templates=contacts_view_templates, listing_about_templates=listing_about_templates, email=flask.session[util.SESS_EMAIL], base_url=config['BASE_URL'], **temp_vals )
def send(recipients, subject, plain_body, html_body=None): """Sends email message through the system-specified email service. @param recipients: The email addresses to send to. @type recipients: Iterable over str @param subject: The email subject line. @type subject: str @param plain_body: The plain text email body. @type plain_body: str @keyword html_body: The HTML email body. @type html_body: str """ app_config = tiny_classified.get_config() if html_body == None: html_body = markdown.markdown(plain_body) if app_config['FAKE_EMAIL']: print '-------' print html_body print '-------' return client = get_service_client( app_config['EMAIL_USERNAME'], app_config['EMAIL_PASSWORD'], app_config['EMAIL_USE_SECURE'] ) message = sendgrid.Mail() message.set_from(app_config['EMAIL_FROM_ADDR']) message.set_subject(subject) message.set_html(html_body) message.set_text(plain_body) for recipient in recipients: message.add_to(recipient) client.web.send(message)
def login(): """Render the login view with login form. @return: The HTML login view. @rtype: str """ flask.session[util.SESS_EMAIL] = None flask.session[util.SESS_IS_ADMIN] = None error = flask.session.get(util.SESS_VALIDATION_ERROR, None) if error: del flask.session[util.SESS_VALIDATION_ERROR] show_reset_password = flask.session.get( util.SESS_VALIDATION_SHOW_RESET, None) if show_reset_password: del flask.session[util.SESS_VALIDATION_SHOW_RESET] confirm = flask.session.get(util.SESS_CONFIRMATION_MSG, None) if confirm: del flask.session[util.SESS_CONFIRMATION_MSG] config = tiny_classified.get_config() temp_vals = tiny_classified.render_common_template_vals() parent_template = config.get( 'PARENT_TEMPLATE', 'tinyclassified_base.html' ) return flask.render_template( 'login/login.html', error=error, confirm=confirm, show_reset_password=show_reset_password, base_url=config['BASE_URL'], parent_template=parent_template, **temp_vals )
def setUp(self): mox.MoxTestBase.setUp(self) tiny_classified.get_config()['FAKE_EMAIL'] = False