Skip to content

Instantly share code, notes, and snippets.

@hardyoyo
Last active October 5, 2020 16:56
Show Gist options
  • Save hardyoyo/85e8e6203877630f73a4a63cd25463db to your computer and use it in GitHub Desktop.
Save hardyoyo/85e8e6203877630f73a4a63cd25463db to your computer and use it in GitHub Desktop.
Scratchpad for developing a Python method to mint DOIs via EZID, WIP
''' a scratch pad for developing the DOI minting method we will use with Janeway '''
# import os
import re
from urllib.parse import quote
import urllib.request as urlreq
from xmltodict import unparse
SHOULDER = 'doi:10.15697/' #for the actual plugin, get the value from the settings.py
USERNAME = 'apitest' #for the actual plugin, get the value from the settings.py
PASSWORD = 'apitest' #for the actual plugin, get the value from the settings.py
ENDPOINT_URL = 'https://uc3-ezidx2-stg.cdlib.org'
#URL = 'https://ezid.cdlib.org' #for the actual plugin, get the value from the settings.py
# staging URL is: https://uc3-ezidx2-stg.cdlib.org in case you need it
TARGET_URL = 'https://escholarship.org/'
class EzidHTTPErrorProcessor(urlreq.HTTPErrorProcessor):
''' Error Processor, required to let 201 responses pass '''
def http_response(self, request, response):
# Bizarre that Python leaves this out.
if response.code == 201:
return response
else:
return urlreq.HTTPErrorProcessor.http_response(self, request, response)
https_response = http_response
def send_create_request(data, shoulder, username, password, endpoint_url):
''' sends a create request to EZID '''
method = "POST"
path = '/shoulder/' + encode(shoulder)
opener = urlreq.build_opener(EzidHTTPErrorProcessor())
ezid_handler = urlreq.HTTPBasicAuthHandler()
ezid_handler.add_password("EZID", endpoint_url, username, password)
opener.add_handler(ezid_handler)
request = urlreq.Request("%s/%s" % (endpoint_url, path))
request.get_method = lambda: method
request.add_header("Content-Type", "text/plain; charset=UTF-8")
request.data = data.encode("UTF-8")
try:
connection = opener.open(request)
response = connection.read()
return response.decode("UTF-8")
except urlreq.HTTPError as ezid_error:
print("%d %s\n" % (ezid_error.code, ezid_error.msg))
if ezid_error.fp is not None:
response = ezid_error.fp.read()
if not response.endswith("\n"):
response += "\n"
print(response)
def encode(txt):
''' encode a text string '''
return quote(txt, ":/")
def mint_doi_via_ezid(shoulder, username, password, endpoint_url, target_url, group_title, contributors, title, posted_date, acceptance_date):
''' Sends a mint request for the specified shoulder, via the EZID url, for the specified target '''
posted_content = {
"posted_content": {
"@xmlns": "http://www.crossref.org/schema/4.4.0",
"@xmlns:xsi": "http://www.w3.org/2001/XMLSchema-instance",
"@xmlns:jats": "http://www.ncbi.nlm.nih.gov/JATS1",
"@xsi:schemaLocation": "http://www.crossref.org/schema/4.4.0 http://www.crossref.org/schema/deposit/crossref4.4.0.xsd",
"group_title": group_title,
"contributors": contributors,
"titles": {
"title": title
},
"posted_date": posted_date,
"acceptance_date": acceptance_date,
"doi_data": {"doi": "10.50505/preprint_sample_doi_2", "resource": "https://escholarship.org/"}
}
}
metadata = unparse(posted_content).replace('\n', '').replace('\r', '')
# uncomment this to validate the metadata payload
# print('\n\n')
# print('Using this metadata:')
# print('\n\n')
# print(unparse(posted_content, pretty=True))
#uncomment this and the import pdb in the imports above to crank up the debugger
#pdb.set_trace()
# These notes will be useful when we move this method to Django, but right now they're useless
# from django.conf import settings
# settings.ezid_shoulder
# settings.ezid_username
# settings.ezid_password
# print('\n\n')
# print('using these values, shoulder: ' + shoulder + '; username: ' + username + '; password: ' + password)
# print('\n\n')
# send the mint request
# print('Sending request to EZID API...\n\n')
# build the payload
payload = 'crossref: ' + metadata + '\n_crossref: yes\n_profile: crossref\n_target: ' + target_url + '\n_owner: ' + username
# print('\n\npayload:\n\n')
# print(payload)
result = send_create_request(payload, shoulder, username, password, endpoint_url)
return result
#### BEGIN MAIN METHOD
if __name__ == "__main__":
GROUP_TITLE = 'Physical Sciences and Mathematics'
TITLE = 'test title, will be deleted'
POSTED_DATE = {"month": "10", "day": "2", "year": "2020"}
ACCEPTANCE_DATE = POSTED_DATE
CONTRIBUTORS = {
"person_name": [
{"@sequence": "first", "@contributor_role": "author", "given_name": "Hardy", "surname": "Pottinger", "ORCID": "https://orcid.org/0000-0001-8549-9354"},
{"@sequence": "additional", "@contributor_role": "author", "given_name": "Marco", "surname": "Psuedonym"},
{"@sequence": "additional", "@contributor_role": "author", "given_name": "Jonathan", "surname": "Alias"},
{"@sequence": "additional", "@contributor_role": "author", "given_name": "Ricardo", "surname": "Nomdeplume"},
{"@sequence": "additional", "@contributor_role": "author", "given_name": "Melissa", "surname": "Unreal"},
{"@sequence": "additional", "@contributor_role": "author", "given_name": "Simon", "surname": "Faker"}]
}
my_result = mint_doi_via_ezid(SHOULDER, USERNAME, PASSWORD, ENDPOINT_URL, TARGET_URL, GROUP_TITLE, CONTRIBUTORS, TITLE, POSTED_DATE, ACCEPTANCE_DATE)
# print(my_result)
if my_result.startswith('success:'):
new_doi = re.search("doi:[0-9A-Z./]+", my_result).group()
print('DOI successfully created: ' + new_doi)
#
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment