def index(): try: deadlines = SPREADSHEETS.worksheet("Deadlines").get_all_records() announcements = SPREADSHEETS.worksheet( "Announcements").get_all_records() return render_template( "home.html", deadlines=[ { **d, # render Markdown in description "description": markdown(d["description"], extensions=[GithubFlavoredMarkdownExtension()]) } for d in deadlines if now(tz="America/New_York").date() <= date_from_str(d["due_date"]).date() ], announcements=reversed([ { **a, # show "3 days ago" or "today" instead of a date, for example "date": "today" if now(tz="America/New_York").date() == date_from_str(a["date"]).date() else date_from_str( a["date"]).humanize(), # render Markdown in description "description": markdown(a["description"], extensions=[GithubFlavoredMarkdownExtension()]) } for a in announcements ])) except gspread.exceptions.APIError: return render_template("home.html", deadlines=[], announcements=[])
def contact(): context = { } query = Article.query(Article.slug == 'contact-page') result = query.fetch(1) if result: context['title'] = result[0].title1 context['title1'] = result[0].title1 context['title2'] = result[0].title2 context['content'] = markdown.markdown( result[0].content, extensions=[GithubFlavoredMarkdownExtension()]) else: logging.error('Contact page not found!') form = ContactLoginForm() if form.validate_on_submit(): msg = ContactMessage() msg.name = form.name.data msg.email = form.email.data msg.message = form.message.data msg.put() return redirect(url_for('main.contact')) return render_template('main/contact_page.html', context=context, form=form, blog_config=blog_config)
def post(slug): context = { } query = Article.query(ndb.AND(Article.slug == slug, Article.published == True)) query = query.fetch() # Our URL slugging has no validation. Similar article titles may create duplicates. # All we are doing is logging a warning so that monitor and manually change duplicated slugs. if len(query) > 1: logging.warn('Duplicate Slug "{}". You should rename one of them to fix this issue'.format(slug)) if query: context['post_title_1'] = query[0].title1 context['post_title_2'] = query[0].title2 context['post_author'] = query[0].author context['title'] = query[0].seo_title context['meta_description'] = query[0].seo_description context['content'] = markdown.markdown( query[0].content, extensions=[GithubFlavoredMarkdownExtension()]) context['created'] = query[0].created # TODO: Find a way of doing this better with css or in the markdown. # Adding the "img-fluid" class for having responsive images context['content'] = context['content'].replace('<img', '<img class="img-fluid"') else: abort(404) return render_template('main/post_page.html', context=context, blog_config=blog_config)
def on_change_body(target, value, oldvalue, initiator): # allowed_tags = ['a','abbr','acronym','b','blockquote','code','em','i','li','ol','pre','strong' # ,'ul','h1','h2','h3','p','img'] target.body_html = markdown( value, output_format='html', extensions=[GithubFlavoredMarkdownExtension()])
def checkUpdates(self, isStartup: bool) -> None: """Check For Updates""" try: url: str = ( "https://api.github.com/repos/Dev-I-J/JNote/releases/latest") with get(url) as r: currentVersionStr: str = "v1.6.13" currentVersion: Version = Version(currentVersionStr) newVersionStr: str = r.json()['tag_name'] newVersion: Version = Version(newVersionStr) if currentVersion < newVersion: raw_info: str = markdown( r.json()['body'], extensions=[GithubFlavoredMarkdownExtension()]) info: str = raw_info.partition( "<h1>Downloads Table</h1>")[0] date: str = r.json()['published_at'][0:10] self.updateInfo["newVersion"] = newVersionStr self.updateInfo["currentVersion"] = currentVersionStr self.updateInfo["details"] = info self.updateInfo["date"] = date self.updateAvailable.emit() elif currentVersion > newVersion: self.apiError.emit() else: if not isStartup: self.updateInfo["currentVersion"] = currentVersionStr self.upToDate.emit() except RequestException: self.apiConnectError.emit() except KeyError: self.apiError.emit() except Exception as e: self.fatalError.emit(str(e), traceback.format_exc())
def _to_html(markdown_text): if not markdown_text: return None # convert markdown to html (replace any <em> tags with bold tags, because <em> is reserved by Algolia md = markdown.markdown(markdown_text, extensions=[GithubFlavoredMarkdownExtension()]) return md.replace('<em>', '<b>').replace('</em>', '</b>')
def main(version, git_version, commit): """ Build the HTML content """ with open('content/ptit-donjon.md') as fd: source = fd.read() body = markdown.markdown(source, extensions=[ GithubFlavoredMarkdownExtension(), TocExtension(permalink=True, slugify=slugify) ]) # Version build if git_version != version: # It's not a tag version = '{}-{}'.format(version, commit) with open('docs/index.html', 'w') as fd: template = Template(TEMPLATE) html = template.substitute({ 'body': body, 'version': version, }) fd.write(html) print('File written: {} bytes'.format(len(html)))
def index(releases, bucket, older_releases=None): with open('site/index.mustache', 'r') as f: template = f.read() released = [ {'name': release.get('name')[1:], 'body': BeautifulSoup(markdown(release.get('body'), extensions=[GithubFlavoredMarkdownExtension()]), 'html.parser').prettify() if release.get('body') else '', 'date': release.get('created_at')[:10]} for release in releases if is_version_uploaded(bucket, get_name(release)) ] if older_releases is not None: released += older_releases renderer = pystache.Renderer(missing_tags='strict') rendered = renderer.render(template, {'releases': released}) bucket.put_object(Key='index.html', Body=rendered, ACL='public-read', ContentType='text/html') site_files = [('site/style.css', 'style.css'), ('site/privacy.html', 'privacy.html')] for source, destination in site_files: with open(source, 'rb') as data: mime_type = mimetypes.guess_type(source)[0] if not mime_type: mime_type = 'application/octet-stream' bucket.put_object(Key=destination, Body=data, ACL='public-read', ContentType=mime_type)
def save(self, *args, **kwargs): self.html = markdown( self.data, extensions=[TableExtension(), GithubFlavoredMarkdownExtension()], safe_mode=True, enable_attributes=False) super(NoteMixin, self).save(*args, **kwargs)
def convert_md_source(source): "Convert Markdown content into HTML" html = markdown.markdown(source, extensions=[ GithubFlavoredMarkdownExtension(), TocExtension(permalink=True, slugify=slugify) ]) return html
def save(self, *args, **kwargs): self.html = markdown(self.data, extensions=[TableExtension(), GithubFlavoredMarkdownExtension()], safe_mode=True, enable_attributes=False) # Define the new card with the greatest priority. if not self.pk and self.ancestor: self.set_priority() super(CardMixin, self).save(*args, **kwargs)
def get_context_data(self, **kwargs): context = super().get_context_data(**kwargs) context['problem'] = Problem.objects.filter(pk=kwargs['problem_id']) context['CTFs'] = Problem.objects.all().values('ctf').order_by('ctf').distinct() context['Categories'] = Problem.objects.all().values('category').order_by('category').distinct() sample_makedown = Problem.objects.get(pk=kwargs['problem_id']).body md = markdown.Markdown(extensions=[GithubFlavoredMarkdownExtension()]) context['text'] = md.convert(sample_makedown) return context
def render_m(self, raw_md): rendered_html = markdown.markdown( raw_md, extensions=[ "codehilite", "sane_lists", GithubFlavoredMarkdownExtension() ], ) print(raw_md) print(rendered_html) return rendered_html
def main(): parser = argparse.ArgumentParser() parser.add_argument('--enable-convert-html', action='store_true') opt_args = parser.parse_args() if opt_args.enable_convert_html: # Third party libraries import markdown from mdx_gfm import GithubFlavoredMarkdownExtension md = markdown.Markdown(extensions=[GithubFlavoredMarkdownExtension()]) mdPathList = glob.glob(os.path.dirname(os.path.abspath(sys.argv[0])) + '/**/*.md', recursive=True) for mdPath in mdPathList: if 'venv' in mdPath: continue print(mdPath) # sys.exit() file_name = os.path.splitext(os.path.basename(mdPath))[0] # print(file_name) if opt_args.enable_convert_html: output = [HEAD_STR.replace('HTML_TITLE', file_name)] s = '' with open(mdPath, mode='r', encoding='utf-8') as f: s = f.read() if 'python' in os.path.dirname(mdPath): p = pathlib.Path(os.path.dirname(os.path.abspath(sys.argv[0]))) project_name = f'{p.parts[-3].upper()}-python' src_str = r'git+https://github.com/GIT_USER_ID/GIT_REPO_ID.git' dst_str = r'"git+https://github.com/y2kblog/poe-webapi-sensor-api.git'\ + f"#egg={project_name}&subdirectory="\ + f"{'/'.join(p.parts[-3:])}/autogen-openapi-generator/python\"" # print(dst_str) s = s.replace(src_str, dst_str) try: with open(mdPath, mode='w', encoding='utf-8') as f: f.write(s) except Exception as e: print(e) if opt_args.enable_convert_html: html_body = md.convert(s) html_body = html_body.replace('.md', '.html') output.append(html_body) output.append(FOOT_STR) # print(output) with open(os.path.join(os.path.dirname(mdPath), file_name + '.html'), mode='w', encoding='utf-8') as f: f.write(''.join(output))
def save(self, *args, **kwargs): self.html = markdown( self.data, extensions=[TableExtension(), GithubFlavoredMarkdownExtension()], safe_mode=True, enable_attributes=False) if not self.pk and self.ancestor: self.set_priority() super(PostMixin, self).save(*args, **kwargs)
def get_context_data(self, **kwargs): context = super().get_context_data(**kwargs) with open(self.request.GET.get('id'), 'r') as myfile: content = myfile.read() i = content.find("---", 3) # Get the ending ---, not the starting one content = content[i + 3:] # Remove the header from content md = markdown.Markdown(extensions=[GithubFlavoredMarkdownExtension()]) html = md.convert(content) context['markdown_content'] = html return context
def to_variables(self, markdown, v, ignore_content=False): def conv_sub_func(match): return sub_func(match, v) markdown = re.sub(self.RE_COMMENTS, conv_sub_func, markdown) html = Markdown(extensions=[GithubFlavoredMarkdownExtension()]).convert(markdown) if not ignore_content: v.variables["content"] = html return v
def get_pull_request(code_repository_id, pull_request_id): github = Github(get_jwt_identity()) code_repository: Repository = github.get_repo( full_name_or_id=int(code_repository_id)) pull_request = code_repository.get_pull(number=int(pull_request_id)) code_comments = map( lambda code_comment: CodeComment.from_github_code_comment(code_comment ), pull_request.get_comments()) return jsonify({ "title": pull_request.title, "codeRepoName": code_repository.name, "userAvatarUrl": pull_request.user.avatar_url, "body": markdown.markdown(pull_request.body, extensions=[GithubFlavoredMarkdownExtension()]), "state": pull_request.state.capitalize(), "comments": list( map( lambda code_comment: code_comment.__dict__, filter(lambda code_comment: code_comment is not None, code_comments))), "files": list( map( lambda file: { "path": file.filename, "ref": pull_request.base.ref if file.status == 'removed' else pull_request.head.ref, "prevRef": pull_request.base.ref, "rawUrl": file.raw_url, "status": file.status, "sha": file.sha, "patch": file.patch }, pull_request.get_files())) })
def parse_markdown(input): """Parses a Markdown input. This wraps around Python Markdown, converting the Markdown string to HTML and sanitizes it. The Markdown flavor used in this app is GFM (GitHub's markdown), and the sanitization depends on the settings specified in sheepyart.py. Args: input(String): A Markdown-formatted string Returns: An HTML-formatted String that has already been sanitized. """ convert = markdown.markdown(input, extensions=[GithubFlavoredMarkdownExtension()]) return scrub.clean(convert)
def send_newsletter(source, config, recipients): smtp = setup_smtp(config) # Load E-Mail contents post = frontmatter.load(source) # Load markdown parser md = markdown.Markdown(extensions=[GithubFlavoredMarkdownExtension()]) with open(config['email']['template'], 'r') as f: html_template = Template(f.read()) markdown_template = Template(post.content) for receiver in recipients: msg = MIMEMultipart('mixed') msg['Subject'] = post['subject'] msg['From'] = config['sender']['sender'] msg['To'] = receiver['email'] msg['Date'] = emailutils.formatdate() msg.preamble = post['subject'] context = receiver.copy() context.update(post) plain = markdown_template.render(**context) context['content'] = md.convert(plain) html = html_template.render(**context) textmsg = MIMEMultipart('alternative') textmsg.attach(MIMEText(plain, 'plain', 'utf-8')) textmsg.attach(MIMEText(html, 'html', 'utf-8')) msg.attach(textmsg) for fname in post.get('attachments', []): fname = os.path.join(os.path.dirname(source), fname) attachment = MIMEApplication(open(fname, 'rb').read()) attachment.add_header('Content-Type', mimetypes.guess_type(fname)[0]) attachment.add_header('Content-Disposition', 'attachment; filename=%s' % os.path.basename(fname)) msg.attach(attachment) print('sending email to %s' % receiver['email']) smtp.sendmail(config['sender']['sender'], receiver['email'], msg.as_string()) smtp.quit()
def render_release_page_html(release_notes_file, release_details): """ Render the Client Application HTML for the specific Release triggered by this event""" # Convert ReleaseNotes to GitHub flavored MarkDown Syntax release_notes = Markup( markdown.markdown(release_notes_file.decode("utf-8"), extensions=[GithubFlavoredMarkdownExtension()])) # Convert Release Date Format release_date = datetime.datetime.strptime(release_details['RELEASE_DATE'], '%Y-%m-%d').strftime('%m/%d/%y') # Determine appropriate CSS based on release type release_version_type_css = release_type_css_switcher( release_details['APPLICATION_RELEASE_TYPE']) # Build S3 Release Download Link based on Release Details release_download_link = 'https://s3.amazonaws.com/' + release_details['S3_BUCKET_NAME'] + '/' \ + release_details['CLIENT_CODE'] + '/applications/' \ + release_details['APPLICATION_CODE'] + '/releases/' \ + release_details['APPLICATION_RELEASE_NAME'] + '.zip' # Set AMI Information - Pending release_ami_region = 'us-east-1' release_ami_identifier = 'Pending' release_ami_locator = 'state=pending' release_ami_link = 'https://console.aws.amazon.com/ec2/v2/home?region=' + release_ami_region + \ '#Images:visibility=private-images;' + release_ami_locator + ';sort=desc:creationDate' # Render the template with the release details j2_env = Environment(loader=FileSystemLoader('templates'), trim_blocks=True) rendered = j2_env.get_template( 'application-release-notes-template.html').render(**locals()) # Push the rendered html page to S3 for consumption encoded_string = rendered.encode("utf-8") destination_key = release_details['CLIENT_CODE'] + '/applications/' + release_details['APPLICATION_CODE'] \ + '/releases/' + release_details['APPLICATION_RELEASE_NAME'] + '-release-notes.html' put_release_html_in_s3_response = s3.put_object( Bucket=release_details['S3_BUCKET_NAME'], Key=destination_key, Body=encoded_string, ContentType='text/html') logger.info(put_release_html_in_s3_response) return rendered
def about(): context = { } query = Article.query(Article.slug == 'about-page') result = query.fetch(1) if result: context['title'] = result[0].title1 context['title1'] = result[0].title1 context['title2'] = result[0].title2 context['content'] = markdown.markdown( result[0].content, extensions=[GithubFlavoredMarkdownExtension()]) else: logging.error('About page not found!') return render_template('main/about_page.html', context=context, blog_config=blog_config)
def list(self, user, page_type): posts = Post.objects.all() owners = [user] if page_type == "stream": for item in user.followers.all(): owners.append(item.followed) posts = posts.filter(owner__in=owners) for post in posts: comments = Comment.objects.filter(commented_post=post) for item in comments: if item.owner == user: item.is_owner = True else: item.is_owner = False post.all_comments = comments post.all_likes = Like.objects.filter(liked_post=post) post.content = markdown.markdown( post.content, extensions=[GithubFlavoredMarkdownExtension()]) return posts
def text_to_markdown(text): """ This method takes any text and sanitizes it from unsafe html tags. Then it converts any markdown syntax into html and returns the result. """ ALLOWED_TAGS = [ 'h1', 'h2', 'h3', 'h4', 'h5', 'h6', 'h7', 'h8', 'br', 'b', 'i', 'span', 'strong', 'em', 'a', 'pre', 'code', 'img', 'tt', 'div', 'ins', 'del', 'sup', 'sub', 'p', 'ol', 'ul', 'table', 'thead', 'tbody', 'tfoot', 'blockquote', 'dl', 'dt', 'dd', 'kbd', 'q', 'samp', 'var', 'hr', 'ruby', 'rt', 'rp', 'li', 'tr', 'td', 'th', 's', 'strike', 'summary', 'details', 'input' ] ALLOWED_ATTRIBUTES = { '*': [ 'abbr', 'accept', 'accept-charset', 'accesskey', 'action', 'align', 'alt', 'axis', 'border', 'cellpadding', 'cellspacing', 'char', 'charoff', 'charset', 'checked', 'clear', 'cols', 'colspan', 'color', 'compact', 'coords', 'datetime', 'dir', 'disabled', 'enctype', 'for', 'frame', 'headers', 'height', 'hreflang', 'hspace', 'ismap', 'label', 'lang', 'maxlength', 'media', 'method', 'multiple', 'name', 'nohref', 'noshade', 'nowrap', 'open', 'prompt', 'readonly', 'rel', 'rev', 'rows', 'rowspan', 'rules', 'scope', 'selected', 'shape', 'size', 'span', 'start', 'summary', 'tabindex', 'target', 'title', 'type', 'usemap', 'valign', 'value', 'vspace', 'width', 'itemprop', 'class', 'checkbox' ], 'a': ['href'], 'img': ['src', 'longdesc'], 'div': ['itemscope', 'itemtype'], 'blockquote': ['cite'], 'del': ['cite'], 'ins': ['cite'], 'q': ['cite'] } markdown_to_html = markdown( text, extensions=[GithubFlavoredMarkdownExtension(), 'codehilite']) sanitized_html = bleach.clean(markdown_to_html, tags=ALLOWED_TAGS, attributes=ALLOWED_ATTRIBUTES) return sanitized_html
def generate_markdown_page(build_path, markdown_page): """Take the markdown dictionary and make it an HTML page.""" has_metadata = markdown_page["has_metadata"] if has_metadata: metadata = markdown_page["metadata"] content = markdown_page["content"] html_body = markdown.markdown( content, extensions=[GithubFlavoredMarkdownExtension()]) base_path = build_path.replace("/build", "") assets_path = f"{base_path}/content/assets/" html = insert_content_blog_template(get_header(assets_path), html_body, get_footer(assets_path), assets_path) new_file_full_path = ( f"{build_path}/{markdown_page['new_path']}{markdown_page['file_name']}.html" ) create_file(html, new_file_full_path)
class MarkdownParser: """ Takes unicode strings and turns them into html Usage: ``` with MarkdownParser(your_markdown_string) as md: print(md.html) ``` """ markdown_parser = Markdown(extensions=[GithubFlavoredMarkdownExtension()]) def __init__(self, unparsed_text: str) -> None: self.unparsed_text: str = unparsed_text self.html: str = mark_safe(self.markdown_parser.convert(unparsed_text)) def __enter__(self) -> "MarkdownParser": return self def __exit__(self, exc_type: Any, exc_value: Any, exc_traceback: Any) -> None: self.markdown_parser.reset()
def generate_enex(): # Note data structure Note = namedtuple('Note', ['title', 'content', 'created', 'updated', 'tags']) # Generate empty XML document soup = BeautifulSoup(features="xml") soup.append(Doctype('en-export SYSTEM "http://xml.evernote.com/pub/evernote-export3.dtd"')) # Everything is wrapped in <en-export> root_tag = soup.new_tag("en-export") # Parse each note original_notes = glob.glob(note_files) for original_note in original_notes: title = os.path.basename(os.path.splitext(original_note)[0]) with open(original_note, 'r') as f: text = f.read() content = markdown.markdown(text, extensions=[GithubFlavoredMarkdownExtension()]) fileinfo = os.stat(original_note) created = time.strftime('%Y%m%dT%H%M%SZ', time.gmtime(fileinfo.st_birthtime)) modified = time.strftime('%Y%m%dT%H%M%SZ', time.gmtime(fileinfo.st_mtime)) tags = extract_tags(original_note) parsed_note = Note(title, content, created, modified, tags) # Append to <en-export> element root_tag.append(create_note(parsed_note, soup)) # Append <en-export> to the empty XML document soup.append(root_tag) with open(out_file, 'w') as f: f.write(str(soup))
def search_page(request): query = request.POST.get("query") if query is None: query = "" users = User.objects.all() posts = Post.objects.all() q1 = Q(username__icontains=query) | Q(first_name__icontains=query) | \ Q(last_name__icontains=query) | Q(email__icontains=query) q2 = Q(title__icontains=query) | Q(content__icontains=query) | \ Q(category__icontains=query) | Q(language__icontains=query) | \ Q(owner__username__icontains=query) | Q(owner__first_name__icontains=query) | \ Q(owner__last_name__icontains=query) | Q(owner__email__icontains=query) users = users.filter(q1) posts = posts.filter(q2) for post in posts: post.content = markdown.markdown(post.content, extensions=[GithubFlavoredMarkdownExtension()]) for user in users: try: Follow.objects.get(follower=request.user, followed=user) user.is_followed = True except Exception as e: user.is_followed = False context = { "query" : query, "users" : users, "posts" : posts } return render(request, 'search.html', context=context)
def detail(request, pk): post = get_object_or_404(Post, pk=pk) comments = Comment.objects.filter(commented_post=post) for item in comments: if item.owner == request.user: item.is_owner = True else: item.is_owner = False post.all_comments = comments post.all_likes = Like.objects.filter(liked_post=post) post.content = markdown.markdown(post.content, extensions=[GithubFlavoredMarkdownExtension()]) print(post.content) if post.owner == request.user: post.is_owner = True else: post.is_owner = False context = { "post" : post } return render(request, 'post.html', context=context)
def markdown_filter(value): return mark_safe(markdown(value, safe_mode='escape', extensions=[GithubFlavoredMarkdownExtension()]))