class BibSonomy::CSL
Attributes
@return [String] the badge type for embedded Altmetric badges. If set to `nil`, no badge is included. (default: `nil`)
@return [Boolean] whether links to BibSonomy
shall be rendered. (default: `true`)
@return [Boolean] whether links to the BibTeX data of a post (in BibSonomy
) shall be rendered. (default: `true`)
@return [String] the CSS class used to render the surrounding `<ul>` list (default: 'publications')
@return [Boolean] whether links for DOIs shall be rendered. (default: `true`)
@return [String] which posts shall be included, based on the groups they are viewable for
@return [String] the separator between options. (default: ' | ')
@return [String] the output directory for downloaded PDF files. If set to `nil`, no documents are downloaded. (default: `nil`)
@return [String] When a post has several documents and the
filename of one of them ends with `public_doc_postfix`, only this document is downloaded and linked, all other are ignored. (default: '_oa.pdf')
@return [String] the {citationstyles.org/ CSL} style used for rendering. (default: `apa.csl`)
@return [Boolean] whether URLs of posts shall be rendered. (default: `true`)
@return [Boolean] whether year headings shall be rendered. (default: `true`)
Public Class Methods
Create a new BibSonomy
instance.
@param user_name [String] the BibSonomy
user name @param api_key [String] the API
key of the user (get at www.bibsonomy.org/settings?selTab=1)
# File lib/bibsonomy/csl.rb, line 95 def initialize(user_name, api_key) super() @bibsonomy = BibSonomy::API.new(user_name, api_key, 'csl') # setting some defaults @style = 'apa.csl' @pdf_dir = nil @css_class = 'publications' @year_headings = true @public_doc_postfix = '_oa.pdf' @group = 'public' @altmetric_badge_type = nil # optional parts to be rendered (or not) @doi_link = true @url_link = true @bibtex_link = true @bibsonomy_link = true @opt_sep = ' | ' end
Public Instance Methods
Download `count` posts for the given `user` and `tag(s)` and render them with {citationstyles.org/ CSL}.
@param grouping [String] the type of the name (either “user” or “group”) @param name [String] the name of the group or user @param tags [Array<String>] the tags that all posts must contain (can be empty) @param count [Integer] number of posts to download @return [String] the rendered posts as HTML
# File lib/bibsonomy/csl.rb, line 123 def render(grouping, name, tags, count) # get posts from BibSonomy posts = JSON.parse(@bibsonomy.get_posts(grouping, name, 'publication', tags, 0, count)) # render them with citeproc cp = CiteProc::Processor.new style: @style, format: 'html' cp.import posts # to check for duplicate file names file_names = [] # filter posts by group # 2017-05-30, rja, disabled until group information is returned by the API # posts.delete_if do |v| # if v["group"] == @group # true # else # print("WARN: " + v["group"]) # false # end # end # sort posts by year sorted_keys = posts.keys.sort { |a,b| get_sort_posts(posts[b], posts[a]) } result = "" # print first heading last_year = 0 if @year_headings and sorted_keys.length > 0 last_year = get_year(posts[sorted_keys[0]]) result += "<h3>" + last_year + "</h3>" end result += "<ul class='#{@css_class}'>\n" for post_id in sorted_keys post = posts[post_id] # print heading if @year_headings year = get_year(post) if year != last_year last_year = year result += "</ul>\n<h3>" + last_year + "</h3>\n<ul class='#{@css_class}'>\n" end end # render metadata csl = cp.render(:bibliography, id: post_id) result += "<li class='" + post["type"] + "'>#{csl[0]}" # extract the post's id intra_hash, user_name = get_intra_hash(post_id) # optional parts options = [] # attach documents if @pdf_dir for doc in get_public_docs(post["documents"]) # fileHash, fileName, md5hash, userName file_path = get_document(@bibsonomy, intra_hash, user_name, doc, @pdf_dir, file_names) options << "<a href='#{file_path}'>PDF</a>" end end # attach DOI doi = post["DOI"] if @doi_link and doi != "" doi, doi_url = get_doi(doi) options << "DOI:<a href='#{doi_url}'>#{doi}</a>" end # attach URL url = post["URL"] if @url_link and url != "" options << "<a href='#{url}'>URL</a>" end # attach BibTeX if @bibtex_link options << "<a href='https://www.bibsonomy.org/bib/publication/#{intra_hash}/#{user_name}'>BibTeX</a>" end # attach link to BibSonomy if @bibsonomy_link options << "<a href='https://www.bibsonomy.org/publication/#{intra_hash}/#{user_name}'>BibSonomy</a>" end # attach options if options.length > 0 result += " <span class='opt'>[" + options.join(@opt_sep) + "]</span>" end # attach Altmetric badge if @altmetric_badge_type and doi != "" doi, doi_url = get_doi(doi) result += "<div class='altmetric-embed' data-badge-type='#{@altmetric_badge_type}' data-doi='#{doi}'></div>" end result += "</li>\n" end result += "</ul>\n" return result end
Private Instance Methods
downloads the documents for the posts (if necessary)
# File lib/bibsonomy/csl.rb, line 297 def get_document(bib, intra_hash, user_name, doc, dir, file_names) # fileHash, fileName, md5hash, userName file_name = doc["fileName"] # strip doc prefix for public documents if file_name.end_with? @public_doc_postfix file_name = file_name[0, file_name.length - @public_doc_postfix.length] + ".pdf" end # check for possible duplicate file names if file_names.include? file_name warn "duplicate file name " + file_name + " for post " + intra_hash end # remember file name file_names << file_name # produce file path file_path = dir + "/" + file_name # download PDF if it not already exists if not File.exists? file_path pdf, mime = bib.get_document(user_name, intra_hash, doc["fileName"]) if pdf == nil warn "could not download file " + intra_hash + "/" + user_name + "/" + file_name else File.binwrite(file_path, pdf) end end return file_path end
given a DOI (or a URL with a DOI) return DOI and resolvable URL
# File lib/bibsonomy/csl.rb, line 233 def get_doi(doi) # simplistic check whether DOI is a URL if doi.start_with?("http") # extract DOI, regex from https://www.crossref.org/blog/dois-and-matching-regular-expressions/ if doi =~ /(10.\d{4,9}\/[-._;()\/:A-Z0-9]+)/i return $1, doi else return doi, doi end else return doi, "https://doi.org/#{doi}" end end
format of the post ID for CSL: [0-9a-f]{32}USERNAME
# File lib/bibsonomy/csl.rb, line 325 def get_intra_hash(post_id) return [post_id[0, 32], post_id[32, post_id.length]] end
only show PDF files
# File lib/bibsonomy/csl.rb, line 277 def get_public_docs(documents) result = [] for doc in documents file_name = doc["fileName"] if file_name.end_with? ".pdf" if documents.length < 2 or file_name.end_with? @public_doc_postfix result << doc end end end return result end
# File lib/bibsonomy/csl.rb, line 260 def get_sort_posts(a, b) person_a = a["author"] if person_a.length == 0 person_a = a["editor"] end person_b = b["author"] if person_b.length == 0 person_b = b["editor"] end # we switch the order of person_b and person_a, to sort # descending by year but ascending by person name return [get_year(a), a["type"], person_b[0]["family"]] <=> [get_year(b), b["type"], person_a[0]["family"]] end
# File lib/bibsonomy/csl.rb, line 247 def get_year(post) issued = post["issued"] # if the post contains only a "year" field, it is contained in # the field "literal" if issued["literal"] return issued["literal"] else # otherwise, the date can be contained in the "raw" field # TODO: extract the year ([12][0-9]{3}) from that field return issued["raw"] end end
# File lib/bibsonomy/csl.rb, line 290 def warn(m) print("WARN: " + m + "\n") end