Created
May 30, 2015 08:51
-
-
Save GaryJones/57974699032c61599d6f to your computer and use it in GitHub Desktop.
bookmarks.gj theme
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| <?php | |
| /** Start the engine **/ | |
| require_once( TEMPLATEPATH . '/lib/init.php' ); | |
| require_once( CHILD_DIR . '/tag_list_widget.php' ); | |
| require_once( CHILD_DIR . '/tag_chain_widget.php' ); | |
| require_once( CHILD_DIR . '/tag_filter_widget.php' ); | |
| /** Add support for custom background **/ | |
| add_theme_support( 'custom-background' ); | |
| /** Add support for custom header **/ | |
| add_theme_support( 'genesis-custom-header', array( 'width' => 960, 'height' => 80 ) ); | |
| remove_theme_support( 'genesis-structural-wraps' ); | |
| add_action( 'genesis_before_loop', 'genesis_bookmarks_query' ); | |
| function genesis_bookmarks_query() { | |
| global $query_string, $paged; | |
| parse_str( $query_string, $query_args ); | |
| $args = array( | |
| 'post_type' => 'bookmark', | |
| ); | |
| query_posts( array_merge( $query_args, $args ) ); | |
| } | |
| remove_action( 'genesis_loop', 'genesis_do_loop' ); | |
| add_action( 'genesis_loop', 'genesisbookmarks_loop' ); | |
| function genesisbookmarks_loop() { | |
| global $loop_counter; | |
| $loop_counter = 0; | |
| if ( have_posts() ) : while ( have_posts() ) : the_post(); // the loop | |
| do_action( 'genesis_before_post' ); | |
| ?> | |
| <li <?php post_class(); ?>> | |
| <?php | |
| do_action( 'genesis_before_post_title' ); | |
| do_action( 'genesis_post_title' ); | |
| do_action( 'genesis_after_post_title' ); | |
| do_action( 'genesis_before_post_content' ); | |
| do_action( 'genesis_post_content' ); | |
| do_action( 'genesis_after_post_content' ); | |
| ?> | |
| </li><!-- end .postclass --> | |
| <?php | |
| do_action( 'genesis_after_post' ); | |
| $loop_counter++; | |
| endwhile; /** end of one post **/ | |
| do_action( 'genesis_after_endwhile' ); | |
| else : /** if no posts exist **/ | |
| do_action( 'genesis_loop_else' ); | |
| endif; /** end loop **/ | |
| } | |
| remove_action( 'genesis_post_content', 'genesis_do_post_content' ); | |
| remove_action( 'genesis_footer', 'genesis_footer_markup_open', 5 ); | |
| remove_action( 'genesis_footer', 'genesis_do_footer' ); | |
| remove_action( 'genesis_footer', 'genesis_footer_markup_close', 15 ); | |
| add_action( 'genesis_before_loop', 'genesisbookmarks_before_loop', 9 ); | |
| function genesisbookmarks_before_loop() { | |
| if ( is_tag() && is_active_sidebar( 'tag-chain-sidebar' ) ) | |
| dynamic_sidebar( 'tag-chain-sidebar' ); | |
| echo '<ul class="bookmarks">'; | |
| } | |
| add_action( 'genesis_after_post', 'genesisbookmarks_after_post', 9 ); | |
| // We call this function, to populate $previousday | |
| function genesisbookmarks_after_post() { | |
| the_date( '', '', '', false ); | |
| } | |
| add_action( 'genesis_after_loop', 'genesisbookmarks_after_loop', 9 ); | |
| function genesisbookmarks_after_loop() { | |
| echo '</ul><!-- end .bookmarks -->'; | |
| } | |
| remove_action( 'genesis_before_post_content', 'genesis_post_info' ); | |
| add_action( 'genesis_before_post_title', 'genesisbookmarks_post_info' ); | |
| function genesisbookmarks_post_info() { | |
| global $post; | |
| $post_info = '<div class="post-info">'; | |
| $post_info .= is_new_day() ? '[post_date format="d M Y"]' : ''; | |
| if ( current_user_can ( 'edit_posts' ) || current_user_can( 'delete_posts' ) ) { | |
| ob_start(); | |
| edit_post_link( __( 'Edit', 'genesisbookmarks' ), '<span class="edit-link">', '</span>' ); | |
| $edit_link = ob_get_clean(); | |
| $post_info .= '<div class="post-actions">' . $edit_link; | |
| $post_info .= current_user_can( 'delete_posts ' ) ? ' | <span class="delete-link"><a href="' . get_delete_post_link( $post->ID, '', false ) . '">' . __( 'Delete', 'genesisbookmarks' ) . '</a></span>' : ''; | |
| $post_info .= '</div>'; | |
| } | |
| $post_info .= '</div>'; | |
| echo apply_filters( 'genesis_post_info', $post_info ); | |
| } | |
| add_filter( 'genesis_post_title_output', 'genesisbookmarks_post_title_output' ); | |
| // Amend title | |
| function genesisbookmarks_post_title_output( $title ) { | |
| global $post; | |
| if ( ! $url = genesis_get_custom_field('link_url') ) | |
| return $title; | |
| return preg_replace( '|href=".*"|', 'href="' . $url . '"', $title ); | |
| } | |
| add_action('genesis_post_content', 'genesisbookmarks_post_content'); | |
| function genesisbookmarks_post_content() { | |
| if( $description = genesis_get_custom_field( 'link_desc' ) ); | |
| echo '<div class="entry-content">' . $description . '</div><!-- end .entry-content -->'; | |
| } | |
| add_filter( 'genesis_post_meta', 'genesisbookmarks_post_meta' ); | |
| function genesisbookmarks_post_meta() { | |
| global $query_string; | |
| parse_str( $query_string, $query_args ); | |
| $tags = get_the_tags(); | |
| foreach ( $tags as $tag ) { | |
| $class = in_array( $tag->slug, explode( '+', isset( $query_args['tag']) ? $query_args['tag'] : '' ) ) ? 'on' : 'off'; | |
| $addition = 'off' == $class && is_tag() ? '<a href="' . get_tag_link( $tag->term_id ) . '+' . get_query_var( 'tag' ) . '" class="add-tag tag-action" title="' . sprintf( __( 'Add %s to tag filter', 'genesisbookmarks'), $tag->name ) . '">+</a>' : ''; | |
| $taglist[] = '<li class="' . $class . ' bookmark-tag tag"><a href="' . get_tag_link($tag->term_id) . '">' . esc_html( $tag->name ) . '</a>' . $addition; | |
| } | |
| if ( $taglist ) | |
| return '<ul class="bookmark-tags">' . implode( ' ', $taglist ) . '</ul>'; | |
| } | |
| //add_filter( 'wp_title', 'genesisbookmarks_title' ); | |
| function genesisbookmarks_title( $title ) { | |
| global $wp_query; | |
| var_dump($wp_query->get_queried_object()); | |
| var_dump(get_query_var( 'tag' )); | |
| if ( ! is_tag() ) | |
| return esc_html( trim( $title ) ); | |
| $tags = explode( '+', get_query_var( 'tag' ) ); | |
| if ( 1 == count( $tags ) ) | |
| return esc_html( trim( $title ) ); | |
| $title = implode( ', ', $tags ); | |
| // if we don't want site name appended, or if we're on the homepage | |
| if ( ! genesis_get_seo_option( 'append_site_title' ) || is_front_page() ) | |
| return esc_html( trim( $title ) ); | |
| $sep = genesis_get_seo_option( 'doctitle_sep' ) ? genesis_get_seo_option( 'doctitle_sep' ) : '–'; | |
| $seplocation = genesis_get_seo_option( 'doctitle_seplocation' ) ? genesis_get_seo_option( 'doctitle_seplocation' ) : 'right'; | |
| // else | |
| $title = 'right' == $seplocation ? $title . " $sep " . get_bloginfo( 'name' ) : get_bloginfo( 'name' ) . " $sep " . $title; | |
| return esc_html( trim( $title ) ); | |
| } | |
| add_action( 'genesis_before_content', 'genesisbookmarks_h1' ); | |
| function genesisbookmarks_h1() { | |
| if ( ! is_tag() ) | |
| return; | |
| $tags = explode( '+', get_query_var( 'tag' ) ); | |
| $tags = array_reverse( $tags ); | |
| $tags = '<span class="tag">' . implode( '</span>, <span class="tag">', $tags ) . '</span>'; | |
| // Negative lookahead assertion to look for non-commas followed by a comma, to replace the last comma with the word "and" | |
| $tags = preg_replace('#,(?![^,]+,)#',' and', $tags); | |
| echo '<h1>Bookmarks tagged with ' . $tags . '</h1>'; | |
| } | |
| remove_action( 'wp_head', 'genesis_canonical' ); | |
| add_action( 'wp_head', 'genesisbookmarks_canonical' ); | |
| function genesisbookmarks_canonical() { | |
| global $wp_query; | |
| $canonical = ''; | |
| if ( is_front_page() ) { | |
| $canonical = trailingslashit( home_url() ); | |
| } | |
| if ( is_singular() ) { | |
| if ( ! $id = $wp_query->get_queried_object_id() ) | |
| return; | |
| $cf = genesis_get_custom_field( '_genesis_canonical_uri' ); | |
| $canonical = $cf ? $cf : get_permalink( $id ); | |
| } | |
| if ( is_category() || is_tag() || is_tax() ) { | |
| if ( !$id = $wp_query->get_queried_object_id() ) | |
| return; | |
| $taxonomy = $wp_query->queried_object->taxonomy; | |
| $canonical = genesis_get_seo_option( 'canonical_archives' ) ? get_term_link( (int) $id, $taxonomy ) : 0; | |
| } | |
| if ( is_tag() ) { | |
| $tags = explode( '+', get_query_var( 'tag' ) ); | |
| sort( $tags ); | |
| $firsttag = get_term_by( 'slug', $tags[0], 'post_tag' ); | |
| $canonical = genesis_get_seo_option( 'canonical_archives' ) ? implode( '+', array( get_tag_link( $firsttag->term_id ), implode( '+', array_diff( $tags, array( $tags[0] ) ) ) ) ) : 0; | |
| } | |
| if ( is_author() ) { | |
| if ( ! $id = $wp_query->get_queried_object_id() ) | |
| return; | |
| $canonical = genesis_get_seo_option( 'canonical_archives' ) ? get_author_posts_url( $id ) : 0; | |
| } | |
| if ( ! $canonical ) | |
| return; | |
| printf( '<link rel="canonical" href="%s" />' . "\n", esc_url( $canonical ) ); | |
| } | |
| add_filter( 'genesis_noposts_text', 'genesisbookmarks_noposts_text' ); | |
| function genesisbookmarks_noposts_text( $text ) { | |
| return __( 'Sorry, no bookmarks could be found with those tags.', 'genesisbookmarks' ); | |
| } | |
| // Register hooks | |
| add_action('wp_enqueue_scripts', 'add_script'); | |
| add_action('wp_footer', 'add_script_config'); | |
| /** | |
| * Add script to admin page | |
| */ | |
| function add_script() { | |
| // Build in tag auto complete script | |
| wp_enqueue_script( 'suggest' ); | |
| } | |
| /** | |
| * add script to admin page | |
| * @todo Get proper URL | |
| */ | |
| function add_script_config() { | |
| ?> | |
| <script type="text/javascript" > | |
| function setSuggest(id) { | |
| jQuery('#' + id).suggest("<?php echo get_bloginfo('wpurl'); ?>/wp-admin/admin-ajax.php?action=ajax-tag-search&tax=post_tag", {multiple:true, multipleSep: "+"}); | |
| } | |
| jQuery(function() { | |
| setSuggest('tag'); | |
| jQuery('#tag-filter').bind('submit.genesisbookmarks', function() { | |
| input = jQuery('#tag').val(); | |
| //alert(input); | |
| input = jQuery.trim(input); | |
| if (input.substr(input.length-1) == '+') { | |
| jQuery('#tag').val(input.substr(0, input.length -1)); | |
| } | |
| //alert(jQuery('#tag').val()); | |
| }); | |
| }); | |
| </script> | |
| <?php | |
| } | |
| genesis_register_sidebar( array( | |
| 'id' => 'tag-chain-sidebar', | |
| 'name' => __( 'Tag Chain Sidebar', 'genesisbookmarks' ), | |
| 'description' => __( 'This is the ideal spot to add the Tag Chain widget, so it appears between the page title and the bookmarks.', 'genesisbookmarks' ), | |
| ) ); |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| <?php | |
| /** | |
| * Add the Tag Chain widget | |
| * | |
| * @package GenesisBookmarks | |
| */ | |
| add_action( 'widgets_init', create_function( '', "register_widget('GenesisBookmarks_Tag_Chain');" ) ); | |
| /** | |
| * Tag Chain widget | |
| * | |
| * @package GenesisBookmarks | |
| * @since 1.0 | |
| * @author Gary Jones | |
| */ | |
| class GenesisBookmarks_Tag_Chain extends WP_Widget { | |
| function GenesisBookmarks_Tag_Chain() { | |
| $widget_ops = array( 'description' => __( 'Displays list of filtered tags.', 'genesisbookmarks' ) ); | |
| $control_ops = array( 'width' => 250, 'height' => 200, 'id_base' => 'tag-chain' ); | |
| $this->WP_Widget( 'tag-chain', __( 'Tag Chain', 'genesisbookmarks' ), $widget_ops, $control_ops ); | |
| } | |
| function widget( $args, $instance ) { | |
| extract( $args ); | |
| // defaults | |
| $instance = wp_parse_args( (array) $instance, array( | |
| 'title' => '', | |
| ) ); | |
| // If tag query is the default empty string, bail out | |
| if ( ! get_query_var( 'tag' ) ) | |
| return; | |
| $tags = explode( '+', get_query_var( 'tag' ) ); | |
| $tags = array_reverse( $tags ); | |
| foreach ( $tags as $atag ) { | |
| // Get the tag object for this tag | |
| $thetag = get_term_by( 'slug', $atag, 'post_tag' ); | |
| // Remove it from the list of all tags, and reindex that list | |
| $minusthistag = array_values( array_diff( $tags, array( $atag ) ) ); | |
| // Get the tag object for the (new) first tag | |
| $firsttag = get_term_by( 'slug', $minusthistag[0], 'post_tag'); | |
| // If there's any other tags left once the first has been accounted for, join them on to the tag link | |
| if ( implode( '+', array_diff( $minusthistag, array( $minusthistag[0] ) ) ) ) | |
| $taglink = implode( '+', array( get_tag_link( $firsttag->term_id ), implode( '+', array_diff( $minusthistag, array( $minusthistag[0] ) ) ) ) ); | |
| else | |
| $taglink = get_tag_link( $firsttag->term_id ); | |
| if ( ! count( $minusthistag ) ) | |
| $taglink = home_url(); | |
| // Trim tag name to max 20 characters. | |
| $thetagname = strlen( $thetag->name ) > 20 ? substr( $thetag->name, 0, 19 ) . '…' : $thetag->name; | |
| $title = strlen( $thetag->name ) > 20 ? $thetag->name : ''; | |
| $tagchain[] = '<li class="tag">' . '<a href="' . get_tag_link( $thetag->term_id ) . '" title="' . $title . '">' . esc_html( $thetagname ) . '</a><a href="' . esc_url( $taglink ) . '" class="remove-tag tag-action" title="Remove ' . esc_attr( strtolower( $thetag->name ) ) . '">X</a></li> '; | |
| } | |
| global $wp_query; | |
| if ( $bookmarks_count = apply_filters( 'genesisbookmarks_bookmarks_count', __( 'Bookmarks: ', 'genesisbookmarks' ) . $wp_query->post_count ) ); | |
| $bookmarks_count = '<span class="bookmarks-count">' . esc_html( $bookmarks_count ) . '</span>'; | |
| if ( $tagchain ) { | |
| echo $before_widget; | |
| if ( ! empty( $instance['title'] ) ) | |
| echo $before_title . apply_filters( 'widget_title', $instance['title'] ) . $after_title; | |
| ?> | |
| <div class="tag-chain"> | |
| <ul><?php echo implode( '', $tagchain ); ?></ul> | |
| <?php /*echo $bookmarks_count;*/ ?> | |
| </div> | |
| <?php | |
| echo $after_widget; | |
| } | |
| } | |
| function update( $new_instance, $old_instance ) { | |
| $instance = $old_instance; | |
| $instance['title'] = strip_tags( $new_instance['title'] ); | |
| return $instance; | |
| } | |
| function form( $instance ) { | |
| //Defaults | |
| $instance = wp_parse_args( (array) $instance, array( | |
| 'title' => '', | |
| ) ); | |
| ?> | |
| <p> | |
| <label id="<?php echo $this->get_field_id( 'title' ); ?>-label" for="<?php echo $this->get_field_id( 'title' ); ?>"><?php _e( 'Title:', 'genesisbookmarks' ); ?></label> | |
| <input class="widefat" id="<?php echo $this->get_field_id( 'title' ); ?>" name="<?php echo $this->get_field_name( 'title' ); ?>" type="text" value="<?php echo $instance['title']; ?>" aria-labelledby="<?php echo $this->get_field_id( 'title' ); ?>-label" /> | |
| </p> | |
| <?php | |
| } | |
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| <?php | |
| /** | |
| * Add the Tag Filter widget | |
| * | |
| * @package GenesisBookmarks | |
| */ | |
| add_action( 'widgets_init', create_function( '', "register_widget('GenesisBookmarks_Tag_Filter');" ) ); | |
| /** | |
| * Tag Filter widget | |
| * | |
| * @package GenesisBookmarks | |
| * @since 1.0 | |
| * @author Gary Jones | |
| */ | |
| class GenesisBookmarks_Tag_Filter extends WP_Widget { | |
| function GenesisBookmarks_Tag_Filter() { | |
| $widget_ops = array( 'description' => __( 'Tag search input with suggestions.', 'genesisbookmarks' ) ); | |
| $control_ops = array( 'width' => 250, 'height' => 200, 'id_base' => 'tag-filter' ); | |
| $this->WP_Widget( 'tag-filter', __( 'Tag Filter', 'genesisbookmarks' ), $widget_ops, $control_ops ); | |
| } | |
| function widget( $args, $instance ) { | |
| extract( $args ); | |
| // defaults | |
| $instance = wp_parse_args( (array) $instance, array( | |
| 'title' => '', | |
| ) ); | |
| echo $before_widget; | |
| if ( ! empty( $instance['title'] ) ) | |
| echo $before_title . apply_filters( 'widget_title', $instance['title'] ) . $after_title; | |
| ?> | |
| <form id="tag-filter" action="" method="GET"> | |
| <input type="text" name="tag" id="tag" /> | |
| </form> | |
| <?php | |
| echo $after_widget; | |
| } | |
| function update( $new_instance, $old_instance ) { | |
| $instance = $old_instance; | |
| $instance['title'] = strip_tags( $new_instance['title'] ); | |
| return $instance; | |
| } | |
| function form( $instance ) { | |
| //Defaults | |
| $instance = wp_parse_args( (array) $instance, array( | |
| 'title' => __( 'Tag Filter', 'genesisbooikmarks' ), | |
| ) ); | |
| ?> | |
| <p> | |
| <label id="<?php echo $this->get_field_id( 'title' ); ?>-label" for="<?php echo $this->get_field_id( 'title' ); ?>"><?php _e( 'Title:', 'genesisbookmarks' ); ?></label> | |
| <input class="widefat" id="<?php echo $this->get_field_id( 'title' ); ?>" name="<?php echo $this->get_field_name( 'title' ); ?>" type="text" value="<?php echo $instance['title']; ?>" aria-labelledby="<?php echo $this->get_field_id( 'title' ); ?>-label" /> | |
| </p> | |
| <?php | |
| } | |
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| <?php | |
| /** | |
| * Add the Tag List widget | |
| * | |
| * @package GenesisBookmarks | |
| */ | |
| add_action( 'widgets_init', create_function( '', "register_widget('GenesisBookmarks_Tag_List');" ) ); | |
| /** | |
| * Tag List widget | |
| * | |
| * @package GenesisBookmarks | |
| * @since 1.0 | |
| * @author Gary Jones | |
| */ | |
| class GenesisBookmarks_Tag_List extends WP_Widget { | |
| function GenesisBookmarks_Tag_List() { | |
| $widget_ops = array( 'description' => __( 'Lists all tags', 'genesisbookmarks' ) ); | |
| $control_ops = array( 'width' => 250, 'height' => 200, 'id_base' => 'tag-list' ); | |
| $this->WP_Widget( 'tag-list', __( 'Tag List', 'genesisbookmarks' ), $widget_ops, $control_ops ); | |
| } | |
| function widget( $args, $instance ) { | |
| extract( $args ); | |
| // defaults | |
| $instance = wp_parse_args( (array) $instance, array( | |
| 'title' => __( 'Tags', 'genesisbookmarks' ), | |
| ) ); | |
| echo $before_widget; | |
| if ( ! empty( $instance['title'] ) ) | |
| echo $before_title . apply_filters( 'widget_title', $instance['title'] ) . $after_title; | |
| ?> | |
| <ul id="tag-list-widget"> | |
| <?php | |
| $term_args = array( | |
| 'orderby' => 'tt.count desc,t.name', | |
| 'number' => $instance['num'], | |
| ); | |
| $tags = get_terms( 'post_tag', $term_args ); | |
| $existing_tags = get_query_var( 'tag' ); | |
| $exploded_tags = explode( '+', $existing_tags ); | |
| //print_r($tags); | |
| foreach ( $tags as $tag ) { | |
| $addition = ''; | |
| if ( $existing_tags ) | |
| $addition = in_array( $tag->slug, $exploded_tags ) ? '' : ' <a href="' . get_tag_link( $tag->term_id ) . '+' . implode( '+', $exploded_tags ) . '" class="addition" title="' . sprintf( __( 'Add %s to tag filter', 'genesisbookmarks'), $tag->name ) . '">' . __( 'Add', 'genesisbookmarks' ) . '</a>'; | |
| $tagname = strlen( $tag->name ) > 30 ? substr( $tag->name, 0, 29 ) . '…' : $tag->name; | |
| $title = strlen( $tag->name ) > 30 ? $tag->name : ''; | |
| echo '<li><a href="' . get_tag_link($tag->term_id) . '" class="tag" title="' . $title . '">' . esc_html( $tagname ) . '</a><span class="count">' . $tag->count . '</span>' . $addition . '</li>'; | |
| } | |
| ?> | |
| </ul> | |
| <?php | |
| echo $after_widget; | |
| } | |
| function update( $new_instance, $old_instance ) { | |
| $instance = $old_instance; | |
| $instance['title'] = strip_tags( $new_instance['title'] ); | |
| $instance['num'] = (int) $new_instance['num']; | |
| return $instance; | |
| } | |
| function form( $instance ) { | |
| //Defaults | |
| $instance = wp_parse_args( (array) $instance, array( | |
| 'title' => __( 'Tags', 'genesisbooikmarks' ), | |
| 'num' => 45, | |
| ) ); | |
| ?> | |
| <p> | |
| <label id="<?php echo $this->get_field_id( 'title' ); ?>-label" for="<?php echo $this->get_field_id( 'title' ); ?>"><?php _e( 'Title:', 'genesisbookmarks' ); ?></label> | |
| <input class="widefat" id="<?php echo $this->get_field_id( 'title' ); ?>" name="<?php echo $this->get_field_name( 'title' ); ?>" type="text" value="<?php echo $instance['title']; ?>" aria-labelledby="<?php echo $this->get_field_id( 'title' ); ?>-label" /> | |
| </p> | |
| <p> | |
| <label id="<?php echo $this->get_field_id( 'num' ); ?>-label" for="<?php echo $this->get_field_id( 'num' ); ?>"><?php _e( 'Number of links to show:', 'genesisbookmarks' ); ?></label> | |
| <input class="widefat" id="<?php echo $this->get_field_id( 'num' ); ?>" name="<?php echo $this->get_field_name( 'num' ); ?>" type="text" value="<?php echo $instance['num']; ?>" aria-labelledby="<?php echo $this->get_field_id( 'title' ); ?>-label" /> | |
| </p> | |
| <?php | |
| } | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment