class Jekyll::APIGenerator

This class generates the GTN’s “api” by writing out a folder full of JSON files.

Public Instance Methods

generate(site) click to toggle source

Runs the generation process Params:

site

Jekyll::Site object

# File _plugins/api.rb, line 118
def generate(site)
  generateConfiguration(site)
  # For some reason the templating isn't working right here.
  # generateVersion(site)
  # TODO:
  # generateLibrary(site)

  Jekyll.logger.info '[GTN/API] Generating API'
  # Full Bibliography
  Gtn::Scholar.load_bib(site)
  Jekyll.logger.debug '[GTN/API] Bibliography'
  page3 = PageWithoutAFile.new(site, '', 'api/', 'gtn.bib')
  page3.content = site.config['cached_global_bib'].to_s
  page3.data['layout'] = nil
  site.pages << page3

  # Metrics endpoint, /metrics
  page2 = PageWithoutAFile.new(site, '', '', 'metrics')
  page2.content = "{% raw %}\n#{Gtn::Metrics.generate_metrics(site)}{% endraw %}"
  page2.data['layout'] = nil
  site.pages << page2

  # Public tool listing
  page2 = PageWithoutAFile.new(site, '', 'api/', 'psl.json')
  page2.content = JSON.generate(site.data['public-server-tools'])
  page2.data['layout'] = nil
  site.pages << page2

  # Tool Categories
  page2 = PageWithoutAFile.new(site, '', 'api/', 'toolcats.json')
  page2.content = JSON.generate(site.data['toolcats'])
  page2.data['layout'] = nil
  site.pages << page2

  # Tool Categories
  page2 = PageWithoutAFile.new(site, '', 'api/', 'toolshed-revisions.json')
  page2.content = JSON.generate(site.data['toolshed-revisions'])
  page2.data['layout'] = nil
  site.pages << page2

  # Feedback Data
  page2 = PageWithoutAFile.new(site, '', 'api/', 'feedback2.json')
  page2.content = JSON.generate(site.data['feedback2'])
  page2.data['layout'] = nil
  site.pages << page2

  # Contributors
  Jekyll.logger.debug '[GTN/API] Contributors, Funders, Organisations'
  %w[contributors grants organisations].each do |type|
    page2 = PageWithoutAFile.new(site, '', 'api/', "#{type}.json")
    page2.content = JSON.pretty_generate(site.data[type].map { |c, _| mapContributor(site, c) })
    page2.data['layout'] = nil
    site.pages << page2
    site.data['contributors'].each do |c, _|
      page4 = PageWithoutAFile.new(site, '', 'api/', "#{type}s/#{c}.json")
      page4.content = JSON.pretty_generate(mapContributor(site, c))
      page4.data['layout'] = nil
      site.pages << page4
    end
  end

  page2 = PageWithoutAFile.new(site, '', 'api/', 'contributors.geojson')
  page2.content = JSON.pretty_generate(
    {
      'type' => 'FeatureCollection',
      'features' => site.data['contributors']
        .select { |_k, v| v.key? 'location' }
        .map do |k, v|
          {
            'type' => 'Feature',
            'geometry' => { 'type' => 'Point', 'coordinates' => [v['location']['lon'], v['location']['lat']] },
            'properties' => {
              'name' => v.fetch('name', k),
              'url' => "https://training.galaxyproject.org/training-material/hall-of-fame/#{k}/",
              'joined' => v['joined'],
              'orcid' => v['orcid'],
              'id' => k,
              'contact_for_training' => v.fetch('contact_for_training', false),
            }
          }
        end
    }
  )
  page2.data['layout'] = nil
  site.pages << page2

  # Trigger the topic cache to generate if it hasn't already
  Jekyll.logger.debug '[GTN/API] Tutorials'
  TopicFilter.topic_filter(site, 'does-not-matter')
  TopicFilter.list_topics(site).map do |topic|
    out = site.data[topic].dup
    out['materials'] = TopicFilter.topic_filter(site, topic).map do |x|
      q = x.dup
      q['contributors'] = Gtn::Contributors.get_contributors(q).dup.map do |c|
        mapContributor(site, c)
      end

      q['urls'] = {}

      if !q['hands_on'].nil?
        q['urls']['hands_on'] = site.config['url'] + site.config['baseurl'] + "/api/topics/#{q['url'][8..-6]}.json"
      end

      if !q['slides'].nil?
        q['urls']['slides'] = site.config['url'] + site.config['baseurl'] + "/api/topics/#{q['url'][8..-6]}.json"
      end

      # Write out the individual page
      page6 = PageWithoutAFile.new(site, '', 'api/topics/', "#{q['url'][7..-6]}.json")
      # Delete the ref to avoid including it by accident
      q.delete('ref')
      q.delete('ref_tutorials')
      q.delete('ref_slides')
      page6.content = JSON.pretty_generate(q)
      page6.data['layout'] = nil
      site.pages << page6

      q
    end
    out['editorial_board'] = out['editorial_board'].map do |c|
      mapContributor(site, c)
    end

    page2 = PageWithoutAFile.new(site, '', 'api/topics/',
                                 "#{topic}.json")
    page2.content = JSON.pretty_generate(out)
    page2.data['layout'] = nil
    site.pages << page2
  end

  topics = {}
  Jekyll.logger.debug '[GTN/API] Topics'
  # Individual Topic Indexes
  site.data.each_pair do |k, v|
    if v.is_a?(Hash) && v.key?('type') && v.key?('editorial_board')

      topics[k] = {
        'name' => v['name'],
        'title' => v['title'],
        'summary' => v['summary'],
        'url' => site.config['url'] + site.config['baseurl'] + "/api/topics/#{k}.json",
        'editorial_board' => v['editorial_board'].map { |c| mapContributor(site, c) }
      }
    end
  end

  # Videos.json
  # {
  # "id": "transcriptomics/tutorials/mirna-target-finder/slides",
  # "topic": "Transcriptomics",
  # "title": "Whole transcriptome analysis of Arabidopsis thaliana"
  # },

  page2 = PageWithoutAFile.new(site, '', 'api/', 'videos.json')
  page2.content = JSON.pretty_generate(TopicFilter.list_videos(site).map do |m|
    {
      id: "#{m['topic_name']}/tutorials/#{m['tutorial_name']}/slides",
      topic: m['topic_name_human'],
      title: m['title']
    }
  end)
  page2.data['layout'] = nil
  site.pages << page2

  # Overall topic index
  page2 = PageWithoutAFile.new(site, '', 'api/', 'topics.json')
  page2.content = JSON.pretty_generate(topics)
  page2.data['layout'] = nil
  site.pages << page2

  Jekyll.logger.debug '[GTN/API] Tutorial and Slide pages'

  # Deploy the feedback file as well
  page2 = PageWithoutAFile.new(site, '', 'api/', 'feedback.json')
  page2.content = JSON.pretty_generate(site.data['feedback'])
  page2.data['layout'] = nil
  site.pages << page2

  # Top Tools
  Jekyll.logger.debug '[GTN/API] Top Tools'
  page2 = PageWithoutAFile.new(site, '', 'api/', 'top-tools.json')
  page2.content = JSON.pretty_generate(TopicFilter.list_materials_by_tool(site))
  page2.data['layout'] = nil
  site.pages << page2

  # Not really an API
  TopicFilter.list_materials_by_tool(site).each do |tool, tutorials|
    page2 = PageWithoutAFile.new(site, '', 'by-tool/', "#{tool.gsub('%20', ' ')}.html")
    page2.content = nil
    page2.data['layout'] = 'by_tool'
    page2.data['short_tool'] = tool
    page2.data['observed_tool_ids'] = tutorials['tool_id']
    page2.data['tutorial_list'] = tutorials['tutorials']
    site.pages << page2
  end

  # GA4GH TRS Endpoint
  # Please note that this is all a fun hack
  TopicFilter.list_all_materials(site).select { |m| m['workflows'] }.each do |material|
    material['workflows'].each do |workflow|
      wfid = workflow['wfid']
      wfname = workflow['wfname']

      page2 = PageWithoutAFile.new(site, '', "api/ga4gh/trs/v2/tools/#{wfid}/versions/", "#{wfname}.json")
      page2.content = JSON.pretty_generate(
        {
          'id' => wfname,
          'url' => site.config['url'] + site.config['baseurl'] + material['url'],
          'name' => 'v1',
          'author' => [],
          'descriptor_type' => ['GALAXY'],
        }
      )
      page2.data['layout'] = nil
      site.pages << page2

      page2 = PageWithoutAFile.new(site, '', "api/ga4gh/trs/v2/tools/#{wfid}/versions/#{wfname}/GALAXY",
                                   'descriptor.json')
      page2.content = JSON.pretty_generate(
        {
          'content' => File.read("#{material['dir']}/workflows/#{workflow['workflow']}"),
          'checksum' => [],
          'url' => nil,
        }
      )
      page2.data['layout'] = nil
      site.pages << page2
    end
  end
end
generateConfiguration(site) click to toggle source

Generates /api/configuration.json Params:

site

Jekyll::Site object

Returns: nil

# File _plugins/api.rb, line 75
def generateConfiguration(site)
  page2 = PageWithoutAFile.new(site, '', 'api/', 'configuration.json')
  site.config.update(Gtn::Git.discover)
  # Remove every key that starts with "cached_"
  conf = site.config.reject { |k, _v| k.to_s.start_with?('cached_') }
  page2.content = JSON.pretty_generate(conf)
  page2.data['layout'] = nil
  site.pages << page2
end
generateLibrary(site) click to toggle source

Generates /api/data-library.yaml Params:

site

Jekyll::Site object

Returns: nil

# File _plugins/api.rb, line 104
def generateLibrary(site)
  Jekyll.logger.info '[GTN/API] Data Library'
  page2 = PageWithoutAFile.new(site, '', 'api/', 'data-library.yaml')
  data_libraries = Dir.glob('topics/**/data-library.yaml')
  data_libraries.map! { |x| YAML.load_file(x) }
  page2.content = JSON.pretty_generate(Gtn::Git.discover)
  page2.data['layout'] = nil
  site.pages << page2
end
generateVersion(site) click to toggle source

Generates /api/version.json Params:

site

Jekyll::Site object

Returns: nil

# File _plugins/api.rb, line 91
def generateVersion(site)
  page2 = PageWithoutAFile.new(site, '', 'api/', 'version.json')
  page2.content = JSON.pretty_generate(Gtn::Git.discover)
  page2.data['layout'] = nil
  site.pages << page2
end