...
 
Commits (2)
No preview for this file type
......@@ -15,3 +15,16 @@ orcid_import.admin_settings:
_title: 'ORCID Import configuration'
requirements:
_permission: 'Administer ORCID configuration'
options:
_admin_route: TRUE
orcid_import.result_page:
path: '/orcid_import/import/{user_orcid_id}'
defaults:
_controller: '\Drupal\orcid_import\Controller\OrcidImporterPageController::content'
_title: 'ORCID Import result'
requirements:
_permission: 'access content'
options:
_admin_route: FALSE
services:
orcid_import.importer:
class: Drupal\orcid_import\Model\Import
arguments: ["user_orcid"]
class: Drupal\orcid_import\Services\OrcidImporter
<?php
namespace Drupal\orcid_import\Controller;
use Drupal\Core\Session\AccountInterface;
use Symfony\Component\HttpFoundation\Request;
use Drupal\orcid_import\Services;
use Drupal\bibcite_entity\Entity\Reference;
class OrcidImporterPageController {
public function content($user_orcid_id) {
$result = \Drupal::service("orcid_import.importer")->importOrcidData($user_orcid_id);
$markup = $this->generateMarkup($result, "", $user_orcid_id);
return $markup;
}
function generateMarkup($result, $type, $user_orcid_id){
$markup = "<div class='container'>";
$markup .= "<h2>Resultado da importação para o ORCID " . $user_orcid_id . ":</h2>";
$markup .= "<div>";
if(intval($result['updated'])>0){
$markup .= "<p> Foram actualizadas " . $result['updated'] . " referências.</p>";
}
if(intval($result['created'])>0){
$markup .= "<p> Foram criadas " . $result['created'] . " referências.</p>";
}
if(count($result['entities']>0)){
$markup .= "<ul>";
foreach($result['entities'] as $ref_id){
$ref_entity = Reference::load($ref_id);
$markup .= "<li><a href='/bibcite/reference/".$ref_id."'>" . $ref_entity->get('title')->getValue()[0]['value'] . "</a></li>";
}
$markup .= "</ul>";
}
$markup .= "</div>";
$markup .= "</div>";
return [
'#markup' => $markup,
];
}
}
<?php
namespace Drupal\orcid_import\Plugin\Block;
use Drupal\Core\Access\AccessResult;
use Drupal\Core\Block\BlockBase;
use Drupal\user\Entity\User;
use Drupal\Core\Form\FormStateInterface;
use Drupal\Core\Session\AccountInterface;
/**
* Provides a block with a ORCID SYNC button.
*
* @Block(
* id = "orcid_import_block",
* admin_label = @Translation("ORCID SYNC Button"),
* )
*/
class OrcidBlock extends BlockBase
{
/**
* {@inheritdoc}
*/
public function build()
{
$current_user_id = \Drupal::currentUser()->id();
$parameters = \Drupal::routeMatch()->getParameters();
$current_user = User::load($current_user_id);
$show_block = ($current_user_id == $parameters->get('user')->id() || \Drupal::currentUser()->hasRole('administrator')) ? true : false;
$orcid_id = $current_user->get('field_orcid')->getValue()[0]['value'];
$variables = [
"import_uid" => $current_user_id,
"import_orcid_id" => $orcid_id,
"show_block" => $show_block,
];
$template_path = drupal_get_path("module", "orcid_import") . "/templates/block--orcid-import.html.twig";
$markup = twig_render_template($template_path, $variables);
return [
'#markup' => $markup,
];
}
/**
* {@inheritdoc}
*/
protected function blockAccess(AccountInterface $account)
{
return AccessResult::allowedIfHasPermission($account, 'access content');
}
/**
* {@inheritdoc}
*/
public function blockForm($form, FormStateInterface $form_state)
{
$config = $this->getConfiguration();
return $form;
}
/**
* {@inheritdoc}
*/
public function blockSubmit($form, FormStateInterface $form_state)
{
$this->configuration['orcid_block_settings'] = $form_state->getValue('orcid_block_settings');
}
}
......@@ -2,6 +2,11 @@
namespace Drupal\orcid_import\Services;
use Drupal\bibcite_entity\Entity\Reference;
use Drupal\bibcite_entity\Entity\Contributor;
use Drupal\bibcite_entity\Entity\Keyword;
use Drupal\user\Entity\User;
/**
* Class OrcidImporter.
*/
......@@ -13,22 +18,293 @@ class OrcidImporter
*/
const LOG_CHANNEL = 'orcid_import';
public function __construct($user_orcid)
{
$this->user_orcid = $user_orcid;
}
/** @const */
private static $bibcite_entity_types = [
'BOOK_CHAPTER' => 'book_chapter',
'CONFERENCE_PAPER' => 'conference_paper',
'JOURNAL_ARTICLE' => 'journal_article',
];
/**
* Fetches data from ORCID and populates Bibcite Entities
*
* @return mixed
* Number of Bibcite entities created and/or updated
* Array of Bibcite entities created and/or updated
*/
public function importOrcidData()
public function importOrcidData($user_orcid)
{
//Do something here to get any data.
\Drupal::logger(self::LOG_CHANNEL)->notice("Fetching ORCID data for user: " . $this->user_orcid);
\Drupal::logger(self::LOG_CHANNEL)->notice("Fetching ORCID data for user: " . $user_orcid);
$url = "https://pub.orcid.org/" . $user_orcid . "/works";
$ch = curl_init();
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
curl_setopt($ch, CURLOPT_HTTPHEADER,[
'Accept: application/vnd.orcid+json',
]);
$curl_result = curl_exec($ch);
$info = curl_getinfo($ch);
curl_close($ch);
$json_data = json_decode($curl_result, true);
$result = $this->processBibciteEntities($json_data, $user_orcid);
return $result;
}
public function processBibciteEntities($json_data, $orcid)
{
$updated_references_count = 0;
$created_references_count = 0;
$referenced_entities = [];
$all_works = $json_data['group'];
$person_data = $this->getOrcidPersonData($orcid);
$user_query = \Drupal::entityQuery('user')
->condition('field_orcid', $orcid)
->execute();
$user_id = reset($user_query);
$user = User::load($user_id);
$author_reference = $user->get("field_author")->referencedEntities();
if (empty($author_reference)) {
// contributor reference doesn't exist; create a new one
$fname = $person_data['name']['given-names']['value'];
$lname = $person_data['name']['family-name']['value'];
$initial = explode(" ", $person_data['name']['credit-name']['value'])[0];
$new_author = Contributor::create([
'type' => 'entity_contributor',
'first_name' => $fname,
'last_name' => $lname,
'leading_title' => $initial,
]);
$new_author->save();
$author_entity_id = $new_author->id();
}else{
$author_entity_id = $author_reference[0]->id();
}
foreach ($all_works as $work) {
$summary = $work['work-summary'][0];
$title = $summary['title']['title']['value'];
$type = self::$bibcite_entity_types[$summary['type']];
$work_put_code = $summary['put-code'];
$query = \Drupal::entityQuery('bibcite_reference')
->condition('title', $title)
->condition('type', $type)
->execute();
$authors_names = $this->getOrcidWorkContributorNames($work_put_code, $orcid);
$contributor_references = $this->processContributorReferences($authors_names, $author_entity_id);
if (!empty($query)) {
// update work reference authors
$bibcite_reference = Reference::load(reset($query));
$bibcite_reference->set('author', $contributor_references);
$bibcite_reference->save();
$updated_references_count++;
$referenced_entities[] = $bibcite_reference->id();
} else {
// create work reference with authors
$work_data = $this->getOrcidWorkData($work_put_code, $orcid);
$work_doi = $this->getOrcidWorkDoi($work_data);
$reference_data = [
'type' => $type,
'title' => $title,
'author' => $contributor_references,
'bibcite_year' => $work_data['publication-date']['year']['value'],
'bibcite_abst_e' => $work_data['short-description'],
'bibcite_url' => $work_doi['url'],
'bibcite_doi' => $work_doi['doi'],
];
$bibcite_reference = Reference::create($reference_data);
$bibcite_reference->save();
$created_references_count++;
$referenced_entities[] = $bibcite_reference->id();
}
}
$result = [
"updated" => $updated_references_count,
"created" => $created_references_count,
"entities" => $referenced_entities,
];
return $result;
}
function getOrcidPersonData($orcid){
$url = "https://pub.orcid.org/" . $orcid;
$ch = curl_init();
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
curl_setopt($ch, CURLOPT_HTTPHEADER,[
'Accept: application/vnd.orcid+json',
]);
$curl_result = curl_exec($ch);
curl_close($ch);
$json_data = json_decode($curl_result, true);
$person_data = $json_data['person'];
return $person_data;
}
function getOrcidWorkContributorNames($work_put_code, $user_orcid) {
$url = "https://pub.orcid.org/" . $user_orcid . "/works/" .$work_put_code;
$ch = curl_init();
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
curl_setopt($ch, CURLOPT_HTTPHEADER,[
'Accept: application/vnd.orcid+json',
]);
$curl_result = curl_exec($ch);
curl_close($ch);
$json_data = json_decode($curl_result, true);
$all_contributors = $json_data['bulk'][0]['work']['contributors']['contributor'];
$contributors_array = array_map(function($item){
return $item['credit-name']['value'];
}, $all_contributors);
return $contributors_array;
}
function processContributorReferences($authors_names, $lead_author_user_id){
$clean_authors = array_map(function($dirty_author_name_string){
$dirty_names = array_reverse(explode(", ", $dirty_author_name_string));
$clean_names = str_replace(".", "", $dirty_names);
return $clean_names;
}, $authors_names);
$contributor_reference_ids = [];
foreach($clean_authors as $author_arr){
$query_author = \Drupal::entityQuery('bibcite_contributor')
->condition('first_name', $author_arr[0]."%", "LIKE")
->condition('last_name', $author_arr[1])
->execute();
if(empty($query_author)){
// contributor does not exist, create one
$new_author = Contributor::create([
'type' => 'entity_contributor',
'last_name' => $author_arr[1],
'first_name' => $author_arr[0].".",
'leading_title' => $author_arr[0].".",
]);
$new_author->save();
$contributor_reference_ids[] = $new_author->id();
}else{
// contributor exists, further checks needed (!!!!)
// for now, add all to contributor reference ids
// only use the first result
$final = reset($query_author);
$contributor_reference_ids = array_merge($contributor_reference_ids, $final);
}
}
// make sure at least ORCID user id is present
if(!in_array($lead_author_user_id, $contributor_reference_ids) || empty($contributor_reference_ids) ) {
array_unshift($contributor_reference_ids, $lead_author_user_id);
}
return $contributor_reference_ids;
}
function getOrcidWorkData($work_put_code, $orcid)
{
$url = "https://pub.orcid.org/" . $orcid . "/works/" .$work_put_code;
$ch = curl_init();
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
curl_setopt($ch, CURLOPT_HTTPHEADER,[
'Accept: application/vnd.orcid+json',
]);
$curl_result = curl_exec($ch);
curl_close($ch);
$json_data = json_decode($curl_result, true);
return $json_data['bulk'][0]['work'];
}
function getOrcidWorkDoi($work_data){
$doi_data = ['url'=>"", "doi"=>""];
$doi_arr = array_filter($work_data['external-ids']["external-id"], function($external_id){
return $external_id["external-id-type"] == "doi";
});
if(!empty($doi_arr)) {
$doi_data['url'] = $doi_arr[0]["external-id-url"]['value'];
$doi_data['doi'] = $doi_arr[0]["external-id-value"];
}
return $doi_data;
}
}
{% if import_uid is not empty and import_orcid_id is not empty %}
{% if show_block == 1 %}
<a id="btn-import-from-authenticus" href="/orcid_import/import/{{ import_orcid_id }}" title="Imports user data from ORCID">ORCID Sync</a>
{% endif %}
{% endif %}
......@@ -77,6 +77,7 @@ module:
node: 0
oai_import: 0
options: 0
orcid_import: 0
page_cache: 0
page_manager: 0
page_manager_ui: 0
......
......@@ -8,6 +8,7 @@ dependencies:
- views.view.user
module:
- ctools_block
- orcid_import
- panels
- views
id: user_profile-panels_variant-0
......@@ -23,7 +24,7 @@ variant_settings:
views_label: ''
items_per_page: none
region: second
weight: 1
weight: -1
uuid: e234ca82-d897-4983-a4a5-1e4a1d6ba718
context_mapping: { }
ada01d2a-b8e9-4d9a-9a66-c6664dbd8ec7:
......@@ -34,7 +35,7 @@ variant_settings:
views_label: ''
items_per_page: none
region: second
weight: 3
weight: 2
uuid: ada01d2a-b8e9-4d9a-9a66-c6664dbd8ec7
context_mapping: { }
10111245-c3b6-4afb-8981-10eea86639aa:
......@@ -49,10 +50,20 @@ variant_settings:
third_party_settings: { }
weight: 0
region: second
weight: 2
weight: 0
uuid: 10111245-c3b6-4afb-8981-10eea86639aa
context_mapping:
entity: user
12cdc6c9-eff6-41c7-8d0a-1046082d36e2:
id: orcid_import_block
label: 'ORCID SYNC Button'
provider: orcid_import
label_display: '0'
region: second
weight: 1
uuid: 12cdc6c9-eff6-41c7-8d0a-1046082d36e2
orcid_block_settings: null
context_mapping: { }
id: panels_variant
uuid: 6812a972-c260-4e63-990d-7e6f237408e2
label: null
......