├── _config_prod.yml
├── .gitignore
├── .github
├── bin
│ └── build_jekyll.sh
└── workflows
│ ├── master.yml
│ └── preview.yml
├── 404.html
├── Bodleian
└── bodleian.json
├── Gemfile
├── _includes
├── header.html
└── social.html
├── _posts
└── 2020-09-30-welcome-to-jekyll.markdown
├── _config.yml
├── Gemfile.lock
├── README.md
├── index.md
└── src
└── createAS.py
/_config_prod.yml:
--------------------------------------------------------------------------------
1 |
2 | url: https://registry.iiif.io
3 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | *.swp
2 | output
3 | _site
4 | .sass-cache
5 | .jekyll-cache
6 | .jekyll-metadata
7 | vendor
8 |
--------------------------------------------------------------------------------
/.github/bin/build_jekyll.sh:
--------------------------------------------------------------------------------
1 | #!/bin/bash
2 |
3 | bundle config path vendor/bundle
4 | if [ $? -eq 1 ];then
5 | echo "Failed adding config path"
6 | exit 1
7 | fi
8 |
9 | bundle install
10 | if [ $? -eq 1 ];then
11 | echo "Failed bundle install"
12 | exit 1
13 | fi
14 |
15 | echo "Running config: $CONFIG"
16 | bundle exec jekyll build --baseurl $BASE_URL $CONFIG
17 | if [ $? -eq 1 ];then
18 | echo "Failed jekyll build"
19 | exit 1
20 | fi
21 |
22 |
--------------------------------------------------------------------------------
/404.html:
--------------------------------------------------------------------------------
1 | ---
2 | permalink: /404.html
3 | layout: default
4 | ---
5 |
6 |
19 |
20 |
21 |
404
22 |
23 |
Page not found :(
24 |
The requested page could not be found.
25 |
26 |
--------------------------------------------------------------------------------
/Bodleian/bodleian.json:
--------------------------------------------------------------------------------
1 | {
2 | "id": "https://www.bodleian.ox.ac.uk/",
3 | "institution": { "en" : ["Bodleian Libraries, University of Oxford"] },
4 | "provider": {
5 | "id": "https://digital.bodleian.ox.ac.uk",
6 | "label": { "en": ["Digital Bodleian: Bodleian Libraries and Oxford College Libraries"] }
7 | },
8 | "streams": [
9 | {
10 | "id": "https://iiif.bodleian.ox.ac.uk/iiif/activity/all-changes",
11 | "label": {"en": ["All changes"]}
12 | }
13 | ]
14 | }
15 |
--------------------------------------------------------------------------------
/Gemfile:
--------------------------------------------------------------------------------
1 | source "https://rubygems.org"
2 | # Hello! This is where you manage which Jekyll version is used to run.
3 | # When you want to use a different version, change it below, save the
4 | # file and run `bundle install`. Run Jekyll with `bundle exec`, like so:
5 | #
6 | # bundle exec jekyll serve
7 | #
8 | # This will help ensure the proper Jekyll version is running.
9 | # Happy Jekylling!
10 | gem "jekyll", "~> 4.1.1"
11 | # This is the default theme for new Jekyll sites. You may change this to anything you like.
12 | gem "minima", "~> 2.5"
13 |
14 | # Windows and JRuby does not include zoneinfo files, so bundle the tzinfo-data gem
15 | # and associated library.
16 | platforms :mingw, :x64_mingw, :mswin, :jruby do
17 | gem "tzinfo", "~> 1.2"
18 | gem "tzinfo-data"
19 | end
20 |
21 | # Performance-booster for watching directories on Windows
22 | gem "wdm", "~> 0.1.1", :platforms => [:mingw, :x64_mingw, :mswin]
23 |
24 |
--------------------------------------------------------------------------------
/_includes/header.html:
--------------------------------------------------------------------------------
1 |
26 |
--------------------------------------------------------------------------------
/_posts/2020-09-30-welcome-to-jekyll.markdown:
--------------------------------------------------------------------------------
1 | ---
2 | layout: post
3 | title: "Welcome to Jekyll!"
4 | date: 2020-09-30 00:28:44 +0100
5 | categories: jekyll update
6 | ---
7 | You’ll find this post in your `_posts` directory. Go ahead and edit it and re-build the site to see your changes. You can rebuild the site in many different ways, but the most common way is to run `jekyll serve`, which launches a web server and auto-regenerates your site when a file is updated.
8 |
9 | Jekyll requires blog post files to be named according to the following format:
10 |
11 | `YEAR-MONTH-DAY-title.MARKUP`
12 |
13 | Where `YEAR` is a four-digit number, `MONTH` and `DAY` are both two-digit numbers, and `MARKUP` is the file extension representing the format used in the file. After that, include the necessary front matter. Take a look at the source for this post to get an idea about how it works.
14 |
15 | Jekyll also offers powerful support for code snippets:
16 |
17 | {% highlight ruby %}
18 | def print_hi(name)
19 | puts "Hi, #{name}"
20 | end
21 | print_hi('Tom')
22 | #=> prints 'Hi, Tom' to STDOUT.
23 | {% endhighlight %}
24 |
25 | Check out the [Jekyll docs][jekyll-docs] for more info on how to get the most out of Jekyll. File all bugs/feature requests at [Jekyll’s GitHub repo][jekyll-gh]. If you have questions, you can ask them on [Jekyll Talk][jekyll-talk].
26 |
27 | [jekyll-docs]: https://jekyllrb.com/docs/home
28 | [jekyll-gh]: https://github.com/jekyll/jekyll
29 | [jekyll-talk]: https://talk.jekyllrb.com/
30 |
--------------------------------------------------------------------------------
/_config.yml:
--------------------------------------------------------------------------------
1 | # Welcome to Jekyll!
2 | #
3 | # This config file is meant for settings that affect your whole blog, values
4 | # which you are expected to set up once and rarely edit after that. If you find
5 | # yourself editing this file very often, consider using Jekyll's data files
6 | # feature for the data you need to update frequently.
7 | #
8 | # For technical reasons, this file is *NOT* reloaded automatically when you use
9 | # 'bundle exec jekyll serve'. If you change this file, please restart the server process.
10 | #
11 | # If you need help with YAML syntax, here are some quick references for you:
12 | # https://learn-the-web.algonquindesign.ca/topics/markdown-yaml-cheat-sheet/#yaml
13 | # https://learnxinyminutes.com/docs/yaml/
14 | #
15 | # Site settings
16 | # These are used to personalize your new site. If you look in the HTML files,
17 | # you will see them accessed via {{ site.title }}, {{ site.email }}, and so on.
18 | # You can create any custom variable you would like, and they will be accessible
19 | # in the templates via {{ site.myvariable }}.
20 |
21 | title: IIIF Registry
22 | description: >- # this means to ignore newlines until "baseurl:"
23 | This is the basis of the IIIF Registry of Activity streams.
24 | url: "https://preview.iiif.io" # the base hostname & protocol for your site, e.g. http://example.com
25 | twitter_username: iiif_io
26 | github_username: IIIF/registry
27 |
28 | # Build settings
29 | theme: minima
30 |
31 | kramdown:
32 | input: GFM
33 | parse_block_html: true
34 | toc_levels: 2..4
35 | #syntax_highlighter: rouge
36 |
37 | syntax_highlighter_opts:
38 | wrap: div
39 | css: class
40 |
41 | webrick:
42 | headers:
43 | Access-Control-Allow-Origin: "*"
44 |
45 | exclude: ["scripts", "Gemfile", "Gemfile.lock", "node_modules", "vendor/bundle/", "vendor/cache/", "vendor/gems/", "vendor/ruby/"]
46 |
--------------------------------------------------------------------------------
/Gemfile.lock:
--------------------------------------------------------------------------------
1 | GEM
2 | remote: https://rubygems.org/
3 | specs:
4 | addressable (2.7.0)
5 | public_suffix (>= 2.0.2, < 5.0)
6 | colorator (1.1.0)
7 | concurrent-ruby (1.1.7)
8 | em-websocket (0.5.2)
9 | eventmachine (>= 0.12.9)
10 | http_parser.rb (~> 0.6.0)
11 | eventmachine (1.2.7)
12 | ffi (1.13.1)
13 | forwardable-extended (2.6.0)
14 | http_parser.rb (0.6.0)
15 | i18n (1.8.5)
16 | concurrent-ruby (~> 1.0)
17 | jekyll (4.1.1)
18 | addressable (~> 2.4)
19 | colorator (~> 1.0)
20 | em-websocket (~> 0.5)
21 | i18n (~> 1.0)
22 | jekyll-sass-converter (~> 2.0)
23 | jekyll-watch (~> 2.0)
24 | kramdown (~> 2.1)
25 | kramdown-parser-gfm (~> 1.0)
26 | liquid (~> 4.0)
27 | mercenary (~> 0.4.0)
28 | pathutil (~> 0.9)
29 | rouge (~> 3.0)
30 | safe_yaml (~> 1.0)
31 | terminal-table (~> 1.8)
32 | jekyll-feed (0.15.0)
33 | jekyll (>= 3.7, < 5.0)
34 | jekyll-sass-converter (2.1.0)
35 | sassc (> 2.0.1, < 3.0)
36 | jekyll-seo-tag (2.6.1)
37 | jekyll (>= 3.3, < 5.0)
38 | jekyll-watch (2.2.1)
39 | listen (~> 3.0)
40 | kramdown (2.3.0)
41 | rexml
42 | kramdown-parser-gfm (1.1.0)
43 | kramdown (~> 2.0)
44 | liquid (4.0.3)
45 | listen (3.2.1)
46 | rb-fsevent (~> 0.10, >= 0.10.3)
47 | rb-inotify (~> 0.9, >= 0.9.10)
48 | mercenary (0.4.0)
49 | minima (2.5.1)
50 | jekyll (>= 3.5, < 5.0)
51 | jekyll-feed (~> 0.9)
52 | jekyll-seo-tag (~> 2.1)
53 | pathutil (0.16.2)
54 | forwardable-extended (~> 2.6)
55 | public_suffix (4.0.6)
56 | rb-fsevent (0.10.4)
57 | rb-inotify (0.10.1)
58 | ffi (~> 1.0)
59 | rexml (3.2.4)
60 | rouge (3.23.0)
61 | safe_yaml (1.0.5)
62 | sassc (2.4.0)
63 | ffi (~> 1.9)
64 | terminal-table (1.8.0)
65 | unicode-display_width (~> 1.1, >= 1.1.1)
66 | unicode-display_width (1.7.0)
67 |
68 | PLATFORMS
69 | ruby
70 |
71 | DEPENDENCIES
72 | jekyll (~> 4.1.1)
73 | kramdown (>= 1.17.0)
74 | minima (~> 2.5)
75 | tzinfo (~> 1.2)
76 | tzinfo-data
77 | wdm (~> 0.1.1)
78 |
79 | BUNDLED WITH
80 | 2.1.4
81 |
--------------------------------------------------------------------------------
/.github/workflows/master.yml:
--------------------------------------------------------------------------------
1 | # This is a basic workflow to help you get started with Actions
2 |
3 | name: Deploy-live
4 |
5 | # Controls when the action will run. Triggers the workflow on push or pull request
6 | # events but only for the master branch
7 | on:
8 | push:
9 | branches:
10 | - master
11 | # A workflow run is made up of one or more jobs that can run sequentially or in parallel
12 | jobs:
13 | # This workflow contains a single job called "build"
14 | build:
15 | # The type of runner that the job will run on
16 | runs-on: ubuntu-latest
17 |
18 | # Steps represent a sequence of tasks that will be executed as part of the job
19 | steps:
20 | # Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it
21 | - uses: actions/checkout@v2
22 |
23 | - name: Setup ruby
24 | uses: actions/setup-ruby@v1
25 | with:
26 | ruby-version: '2.7'
27 | - run: gem install bundler
28 |
29 | - uses: actions/cache@v1
30 | with:
31 | path: vendor/bundle
32 | key: ${{ runner.os }}-gems-${{ hashFiles('**/Gemfile.lock') }}
33 | restore-keys: |
34 | ${{ runner.os }}-gems-
35 |
36 | # Build jekyll site
37 | - name: Build Jekyll
38 | run: .github/bin/build_jekyll.sh
39 | env:
40 | CONFIG: "--config _config.yml,_config_prod.yml"
41 | BASE_URL: "/"
42 | # build streams
43 | - name: Set up Python 3.x
44 | uses: actions/setup-python@v2
45 | with:
46 | # Semantic version range syntax or exact version of a Python version
47 | python-version: '3.x'
48 | # Optional - x64 or x86 architecture, defaults to x64
49 | architecture: 'x64'
50 |
51 | - name: Create streams
52 | run: src/createAS.py
53 |
54 |
55 | # Deploy to live site
56 | - name: Create GitHub deployment
57 | uses: glenrobson/deployments@v0.4.2
58 | id: deployment
59 | with:
60 | step: start
61 | token: ${{ secrets.GITHUB_TOKEN }}
62 | auto_inactive: 'false'
63 | env: production
64 | - name: Deploy to S3
65 | uses: glenrobson/s3-sync-action@v0.5.1
66 | with:
67 | args: --acl public-read --cache-control max-age=0,public
68 | env:
69 | AWS_S3_BUCKET: "iiif-registry"
70 | AWS_ACCESS_KEY_ID: ${{ secrets.AWS_ACCESS_KEY_ID }}
71 | AWS_SECRET_ACCESS_KEY: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
72 | AWS_REGION: ${{ secrets.AWS_REGION }}
73 | SOURCE_DIR: "_site"
74 | - name: Update deployment status
75 | uses: glenrobson/deployments@v0.4.2
76 | if: always()
77 | with:
78 | step: finish
79 | auto_inactive: 'false'
80 | token: ${{ secrets.GITHUB_TOKEN }}
81 | status: ${{ job.status }}
82 | deployment_id: ${{ steps.deployment.outputs.deployment_id }}
83 | env_url: "https://registry.iiif.io"
84 |
--------------------------------------------------------------------------------
/.github/workflows/preview.yml:
--------------------------------------------------------------------------------
1 | # This is a basic workflow to help you get started with Actions
2 |
3 | name: Deploy-preview
4 |
5 | # Controls when the action will run. Triggers the workflow on push or pull request
6 | # events but only for the master branch
7 | on:
8 | push:
9 | branches:
10 | - '*'
11 | - '!master'
12 | # A workflow run is made up of one or more jobs that can run sequentially or in parallel
13 | jobs:
14 | # This workflow contains a single job called "build"
15 | build:
16 | # The type of runner that the job will run on
17 | runs-on: ubuntu-latest
18 |
19 | # Steps represent a sequence of tasks that will be executed as part of the job
20 | steps:
21 | # Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it
22 | - uses: actions/checkout@v2
23 | # store branch name in ${BRANCH_NAME}
24 | - uses: nelonoel/branch-name@v1.0.1
25 |
26 | - name: Setup ruby
27 | uses: actions/setup-ruby@v1
28 | with:
29 | ruby-version: '2.7'
30 | - run: gem install bundler
31 |
32 | - uses: actions/cache@v1
33 | with:
34 | path: vendor/bundle
35 | key: ${{ runner.os }}-gems-${{ hashFiles('**/Gemfile.lock') }}
36 | restore-keys: |
37 | ${{ runner.os }}-gems-
38 |
39 | # Build jekyll site
40 | - name: Build Jekyll
41 | run: .github/bin/build_jekyll.sh
42 | env:
43 | CONFIG: "--config _config.yml"
44 | BASE_URL: "/registry/${{ env.BRANCH_NAME}}"
45 |
46 | # Create streams
47 | - name: Set up Python 3.x
48 | uses: actions/setup-python@v2
49 | with:
50 | # Semantic version range syntax or exact version of a Python version
51 | python-version: '3.x'
52 | # Optional - x64 or x86 architecture, defaults to x64
53 | architecture: 'x64'
54 |
55 | - name: Create streams
56 | run: src/createAS.py
57 |
58 | # Deploy to live site
59 | - name: Create GitHub deployment
60 | uses: glenrobson/deployments@v0.4.2
61 | id: deployment
62 | with:
63 | step: start
64 | token: ${{ secrets.GITHUB_TOKEN }}
65 | auto_inactive: 'false'
66 | env: staging
67 | - name: Deploy to S3
68 | uses: glenrobson/s3-sync-action@v0.5.1
69 | with:
70 | args: --acl public-read
71 | env:
72 | AWS_S3_BUCKET: "preview.iiif.io"
73 | AWS_ACCESS_KEY_ID: ${{ secrets.AWS_ACCESS_KEY_ID }}
74 | AWS_SECRET_ACCESS_KEY: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
75 | AWS_REGION: ${{ secrets.AWS_REGION }}
76 | SOURCE_DIR: "_site"
77 | DEST_DIR: "registry/${BRANCH_NAME}"
78 | - name: Update deployment status
79 | uses: glenrobson/deployments@v0.4.2
80 | if: always()
81 | with:
82 | step: finish
83 | auto_inactive: 'false'
84 | token: ${{ secrets.GITHUB_TOKEN }}
85 | status: ${{ job.status }}
86 | deployment_id: ${{ steps.deployment.outputs.deployment_id }}
87 | env_url: "https://preview.iiif.io/registry/${{ env.BRANCH_NAME}}/index.html"
88 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # IIIF Registry
2 | This is the basis of the IIIF Registry of Activity streams. This project aims to give access to a large amount of IIIF resources and provide a way to keep up to date with changes. The Activity Streams format is defined in the [Change Discovery Specification](https://iiif.io/api/discovery/0.4/).
3 |
4 | We welcome additions to the registry and additions can be made using the following process:
5 |
6 | 1. Create branch for your addition
7 | 2. Create a directory for your institution. This should be a short name without spaces or punctuation
8 | 3. Create a registry JSON file. See details below
9 | 4. Create a pull request with your changes and submit to IIIF/registry
10 |
11 | ## Registry JSON format
12 |
13 | To register a link to your streams we use the following JSON structure:
14 |
15 | ```
16 | {
17 | "id": "http://www.getty.edu/",
18 | "institution": {
19 | "id": "http://www.getty.edu/",
20 | "label": {
21 | "en": [ "Getty" ]
22 | }
23 | },
24 | "streams": [
25 | {
26 | "id": "http://www.getty.edu/museum.json",
27 | "label": {
28 | "en": [ "Museum collections" ]
29 | }
30 | },
31 | {
32 | "id": "http://www.getty.edu/library.json",
33 | "label": {
34 | "en": [ "Library collections" ]
35 | }
36 | },
37 | {
38 | "id": "http://www.getty.edu/research.json",
39 | "label": {
40 | "en": [ "Research Center" ]
41 | }
42 | }
43 | ]
44 | }
45 | ```
46 |
47 | Where:
48 | * `id` is a URI for your institution. This could be an institution website, Wikidata URI or other resolvable link.
49 | * `institution` the name of the institution that could be shown to a user. This is an optional field but encouraged.
50 | * `streams` list of activity streams for this institution
51 | * `id` Activity Stream URL. Must be resolvable
52 | * `label` a description that can be shown to the user so they can tell which stream to monitor for updates.
53 |
54 | The JSON file should be named appropriately so people know what it represents and must have an extension of `.json`.
55 |
56 | ## Aggregators
57 |
58 | For Aggregators or institutions that collect content from other providers and aggregate their content. A slightly different structure can be used. Examples of Aggregators would be Europeana or OCLC with ContentDM. Both hold multiple institutions' data. In this case the Aggregator would have one registry JSON file per institutional client. The Provider can then add the following to the root of the JSON to show who provided the content:
59 |
60 | ```
61 | "provider": {
62 | "id": "https://www.oclc.org/en/home.html",
63 | "label": {
64 | "en": [ "OCLC" ]
65 | }
66 | },
67 | ```
68 |
69 | You can see examples of this in the [OCLC directory](https://github.com/IIIF/registry/tree/deploy/OCLC) where [instx.json](https://github.com/IIIF/registry/blob/deploy/OCLC/instx.json) would be the set of changes from one ContentDM instance and [insty.json](https://github.com/IIIF/registry/blob/deploy/OCLC/insty.json) is a second institution.
70 |
--------------------------------------------------------------------------------
/index.md:
--------------------------------------------------------------------------------
1 | ---
2 | title: IIIF Registry
3 | layout: default
4 | tags: [tbc]
5 | summary: "tbc"
6 | ---
7 |
8 | # IIIF Registry
9 | This is the basis of the IIIF Registry of Activity streams. This project aims to give access to a large amount of IIIF resources and provide a way to keep up to date with changes. The Activity Streams format is defined in the [Change Discovery Specification](https://iiif.io/api/discovery/0.4/).
10 |
11 | We welcome additions to the registry and additions can be made using the following process:
12 |
13 | 1. Create branch for your addition
14 | 2. Create a directory for your institution. This should be a short name without spaces or punctuation
15 | 3. Create a registry JSON file. See details below
16 | 4. Create a pull request with your changes and submit to IIIF/registry
17 |
18 | ## Registry JSON format
19 |
20 | To register a link to your streams we use the following JSON structure:
21 |
22 | ```
23 | {
24 | "id": "http://www.getty.edu/",
25 | "institution": {
26 | "id": "http://www.getty.edu/",
27 | "label": {
28 | "en": [ "Getty" ]
29 | }
30 | },
31 | "streams": [
32 | {
33 | "id": "http://www.getty.edu/museum.json",
34 | "label": {
35 | "en": [ "Museum collections" ]
36 | }
37 | },
38 | {
39 | "id": "http://www.getty.edu/library.json",
40 | "label": {
41 | "en": [ "Library collections" ]
42 | }
43 | },
44 | {
45 | "id": "http://www.getty.edu/research.json",
46 | "label": {
47 | "en": [ "Research Center" ]
48 | }
49 | }
50 | ]
51 | }
52 | ```
53 |
54 | Where:
55 | * `id` is a URI for your institution. This could be an institution website, Wikidata URI or other resolvable link.
56 | * `institution` the name of the institution that could be shown to a user. This is an optional field but encouraged.
57 | * `streams` list of activity streams for this institution
58 | * `id` Activity Stream URL. Must be resolvable
59 | * `label` a description that can be shown to the user so they can tell which stream to monitor for updates.
60 |
61 | The JSON file should be named appropriately so people know what it represents and must have an extension of `.json`.
62 |
63 | ## Aggregators
64 |
65 | For Aggregators or institutions that collect content from other providers and aggregate their content. A slightly different structure can be used. Examples of Aggregators would be Europeana or OCLC with ContentDM. Both hold multiple institutions' data. In this case the Aggregator would have one registry JSON file per institutional client. The Provider can then add the following to the root of the JSON to show who provided the content:
66 |
67 | ```
68 | "provider": {
69 | "id": "https://www.oclc.org/en/home.html",
70 | "label": {
71 | "en": [ "OCLC" ]
72 | }
73 | },
74 | ```
75 |
76 | You can see examples of this in the [OCLC directory](https://github.com/IIIF/registry/tree/deploy/OCLC) where [instx.json](https://github.com/IIIF/registry/blob/deploy/OCLC/instx.json) would be the set of changes from one ContentDM instance and [insty.json](https://github.com/IIIF/registry/blob/deploy/OCLC/insty.json) is a second institution.
77 |
--------------------------------------------------------------------------------
/_includes/social.html:
--------------------------------------------------------------------------------
1 |
15 |
--------------------------------------------------------------------------------
/src/createAS.py:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env python3
2 |
3 | import json
4 | import math
5 |
6 | from os import listdir
7 | from os.path import isfile, join, isdir, exists
8 | import os
9 | import re
10 |
11 | ignore_list = ['[.]+.*', 'src', '_site']
12 |
13 | def processDir(path):
14 | files = []
15 | for fileName in listdir(path):
16 | ignore=False
17 | for ignoreStr in ignore_list:
18 | if re.match(ignoreStr, fileName):
19 | #print ('Ignoring {} with {}'.format(fileName, ignoreStr))
20 | ignore=True
21 | break
22 | if not ignore:
23 | if isdir(fileName):
24 | files.extend(processDir(fileName))
25 | elif fileName[-5:] == '.json':
26 | #print ('Adding {}'.format(fileName))
27 | files.append('{}/{}'.format(path, fileName))
28 | #else:
29 | # print ('Ignoring {} as its not json'.format(fileName))
30 |
31 | return files
32 |
33 |
34 |
35 | files = processDir('.')
36 | print ('Found files {}'.format(files))
37 | pageLimit = 10
38 | asStreams = []
39 | for jsonFile in files:
40 | print ('Opening: {}'.format(jsonFile))
41 | with open(jsonFile) as json_file:
42 | data = json.load(json_file)
43 | for stream in data['streams']:
44 | asStream = {
45 | 'id': stream['id'],
46 | 'label': stream['label']
47 | }
48 | if 'provider' in data:
49 | asStream['provider'] = data['provider']
50 | if 'institution' in data:
51 | asStream['source'] = data['institution']
52 | asStreams.append(asStream)
53 |
54 | # should now sort asStream in some way to ensure the newest are first.
55 |
56 | # Now write out streams to pages
57 | startIndex = 0
58 | if len(asStreams) > pageLimit:
59 | endIndex = pageLimit
60 | else:
61 | endIndex = len(asStreams)
62 |
63 | pageCount = 0
64 | maxPages = math.ceil(len(asStreams) / pageLimit)
65 | pageJson = []
66 | baseURL = "https://registry.iiif.io"
67 | firstRun = True
68 | while endIndex < len(asStreams) or firstRun==True:
69 | print ('endIndex {} asStreams length {}'.format(endIndex, len(asStreams)))
70 | currentPage = {
71 | "@context": "http://iiif.io/api/discovery/1/context.json",
72 | "id": "{}/page-{}.json".format(baseURL, pageCount),
73 | "type": "OrderedCollectionPage",
74 | "partOf": {
75 | "id": "{}/index.json".format(baseURL),
76 | "type": "OrderedCollection"
77 | }
78 | }
79 | if pageCount != 0:
80 | currentPage["prev"] = {
81 | "id": "{}/page-{}".format(baseURL, pageCount - 1),
82 | "type": "OrderedCollectionPage"
83 | }
84 | print ('Page count {}, maxPages {}'.format(pageCount, maxPages))
85 | if pageCount < (maxPages - 1):
86 | currentPage["next"] = {
87 | "id": "{}/page-{}".format(baseURL, pageCount + 1),
88 | "type": "OrderedCollectionPage"
89 | }
90 | currentPage['orderedItems'] = []
91 | for i in range(startIndex, endIndex):
92 | activity = {
93 | 'type': 'Update',
94 | 'object': {
95 | 'id': asStreams[i]['id'],
96 | 'type': 'OrderedCollection',
97 | 'nameMap': asStreams[i]['label']
98 | }
99 | }
100 | if 'source' in asStreams[i] or 'provider' in asStreams[i]:
101 | activity['actor'] = []
102 | if 'source' in asStreams[i]:
103 | actor = asStreams[i]['source']
104 | if 'type' not in actor:
105 | actor['type'] = "Organization"
106 |
107 | activity['actor'].append(actor)
108 |
109 | if 'provider' in asStreams[i]:
110 | actor = asStreams[i]['provider']
111 | if 'type' not in actor:
112 | actor['type'] = "Organization"
113 |
114 | activity['actor'].append(actor)
115 |
116 |
117 | currentPage['orderedItems'].append(activity)
118 |
119 |
120 | pageJson.append(currentPage)
121 |
122 | firstRun = False
123 | startIndex = endIndex
124 | pageCount += 1
125 | if len(asStreams) - endIndex > pageLimit:
126 | endIndex += pageLimit
127 | else:
128 | endIndex = len(asStreams)
129 |
130 | pageCount = 1
131 | outputDir = '_site'
132 | if not exists(outputDir):
133 | os.mkdir(outputDir)
134 |
135 | for page in pageJson:
136 | print ('Page: {}'.format(pageCount))
137 | print (json.dumps(page, indent=4))
138 | filename = page['id'].split('/')[-1]
139 | with open('{}/{}'.format(outputDir, filename), 'w') as outfile:
140 | json.dump(page, outfile, indent=4)
141 | pageCount += 1
142 |
143 | # Now create index.json
144 |
145 | index = {
146 | "@context": "http://iiif.io/api/discovery/1/context.json",
147 | "id": "https://registry.iiif.io/index.json",
148 | "type": "OrderedCollection",
149 | "summary": "The IIIF registry of Activity Streams",
150 | "first": {
151 | "id": "https://registry.iiif.io/page-0.json",
152 | "type": "OrderedCollectionPage"
153 | },
154 | "last": {
155 | "id": "https://registry.iiif.io/page-{}.json".format(pageCount - 2),
156 | "type": "OrderedCollectionPage"
157 | }
158 | }
159 |
160 | with open('{}/index.json'.format(outputDir), 'w') as outfile:
161 | json.dump(index, outfile, indent=4)
162 |
--------------------------------------------------------------------------------