Created
May 5, 2014 08:20
-
-
Save mjlassila/86da5719ac420e7fdf2f to your computer and use it in GitHub Desktop.
XQuery module for creating MARC21 records
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
module namespace marc = 'app.marc.generator'; | |
declare function marc:zero-prefix-time($timestamp as xs:string) { | |
let $time:=xs:string($timestamp) | |
let $prefixed_time:= | |
if(string-length($time) < 2) then | |
concat(0,$time) | |
else $time | |
return $prefixed_time | |
}; | |
declare function marc:create-marc-timestamp($context as xs:string) as xs:string { | |
let $timestamp:=fn:current-dateTime() | |
let $year:=xs:string(fn:year-from-dateTime($timestamp)) | |
let $month:=marc:zero-prefix-time(xs:string(fn:month-from-dateTime($timestamp))) | |
let $day:=marc:zero-prefix-time(xs:string(fn:day-from-dateTime($timestamp))) | |
let $hours:=marc:zero-prefix-time(xs:string(fn:hours-from-dateTime($timestamp))) | |
let $minutes:=marc:zero-prefix-time(xs:string(fn:minutes-from-dateTime($timestamp))) | |
let $seconds:=substring-before(marc:zero-prefix-time(xs:string(fn:seconds-from-dateTime($timestamp))),'.') | |
let $marc-timestamp:= | |
if($context eq '005') then | |
concat($year,$month,$day,$hours,$minutes,$seconds,'.0') | |
else if ($context eq '008') then | |
concat(substring($year,3,2),$month,$day) | |
else() | |
return $marc-timestamp | |
}; | |
declare function marc:leader($series as element(isbnFormSeries)?) as element(){ | |
let $bibliographic_level:= | |
if (string-length($series)>2) then | |
's' | |
else ('m' | |
) | |
return | |
<leader>{concat('00000na',$bibliographic_level,' a22000008i 4500')}</leader> | |
}; | |
declare function marc:field-001($node as element(btitle)) as element() { | |
<controlfield tag="001">69876</controlfield> | |
}; | |
declare function marc:field-005() as element() { | |
<controlfield tag="005">{marc:create-marc-timestamp('005')}</controlfield> | |
}; | |
declare function marc:field-008($year as element(isbnFormPublishingYear)?, $language as element()?) as element() { | |
let $timestamp:=marc:create-marc-timestamp('008') | |
let $publishing_date_type:='s' | |
let $publishing_date:=if ($year) then | |
$year | |
else ('||||') | |
let $publishing_date_spacer:=' ' | |
let $place_of_publication:='fi' | |
let $filler:=' ||||||| |||||||' | |
let $language:= | |
if (contains($language,'fi')) then | |
'fin' | |
else if (contains($language,'sv')) then | |
'swe' | |
else if (contains($language,'en')) then | |
'eng' | |
else ( | |
'fin' | |
) | |
let $trailing_filler:='||' | |
return <controlfield tag="008">{ | |
concat( | |
$timestamp, | |
$publishing_date_type, | |
$publishing_date, | |
$publishing_date_spacer, | |
$place_of_publication, | |
$filler, | |
$language, | |
$trailing_filler | |
)}</controlfield> | |
}; | |
declare function marc:field-020($isbn as element(isbnFormISBN), $format as element(isbnFormFormat)) as element() { | |
<datafield tag="020" ind1=" " ind2=" "> | |
<subfield code="a">{data($isbn)}</subfield> | |
<subfield code="q">{data($format)}</subfield> | |
</datafield> | |
}; | |
declare function marc:field-041($language as element(isbnFormLang)?) as element() { | |
let $subfield_a:= | |
if (string-length($language) eq 3) then | |
<subfield code="a">{data($language)}</subfield> | |
else ( | |
<subfield code="a">fin</subfield> | |
) | |
return | |
<datafield tag="041" ind1="0" ind2=" "> | |
{$subfield_a} | |
</datafield> | |
}; | |
declare function marc:field-100($author as node()*) as element()? { | |
let $subfield_e:= | |
if (string-length($author/@role)>2) then | |
<subfield code="e">{concat($author/@role,'.')}</subfield> | |
else() | |
return | |
(:Onko kyseessä teos, jolla on päävastuullinen tekijä?:) | |
if(string-length($author/@surname)>=2) then | |
<datafield tag="100" ind1="1" ind2=" "> | |
<subfield code="a">{concat($author/@surname,', ',$author/@firstname,',')}</subfield> | |
<subfield code="c">ennakkotieto.</subfield> | |
{$subfield_e} | |
</datafield> | |
else() | |
}; | |
declare function marc:field-245($title as element(isbnFormTitle), $subtitle as element(isbnFormSubtitle)*) as element() { | |
let $subfield_b:= | |
if(string-length($subtitle)>2) then | |
<subfield code="b">{concat(data($subtitle),'.')}</subfield> | |
else () | |
let $subfield_a:= | |
if(string-length($subtitle)>2) then | |
<subfield code="a">{concat(data($title),' :')}</subfield> | |
else ( | |
<subfield code="a">{data($title)}</subfield> | |
) | |
return | |
<datafield tag="245" ind1="1" ind2="0"> | |
{$subfield_a} | |
{$subfield_b} | |
</datafield> | |
}; | |
declare function marc:field-260($publisher as element(isbnFormPublishingHouse), $year as element(isbnFormPublishingYear)) as element()? { | |
let $subfield_b:= | |
if(string-length($publisher)>2 and string-length($year)>2) then | |
<subfield code="b">{concat(data($publisher),',')}</subfield> | |
else if (string-length($publisher)>2) then | |
<subfield code="b">{data($publisher)}</subfield> | |
else () | |
let $subfield_c:= | |
if(string-length($publisher)>2 and string-length($year)>2) then | |
<subfield code="c">{concat(data($year),'.')}</subfield> | |
else () | |
return | |
if ($subfield_b and $subfield_c) then | |
<datafield tag="260" ind1=" " ind2=" "> | |
{$subfield_b} | |
{$subfield_c} | |
</datafield> | |
else() | |
}; | |
declare function marc:field-263($year as element(isbnFormPublishingYear)) as element() { | |
<datafield tag="263" ind1=" " ind2=" "> | |
<subfield code="a">{concat(data($year),'--')}</subfield> | |
</datafield> | |
}; | |
declare function marc:field-336() as element() { | |
<datafield tag="336" ind1=" " ind2=" "> | |
<subfield code="a">Teksti</subfield> | |
</datafield> | |
}; | |
declare function marc:field-337() as element() { | |
<datafield tag="337" ind1=" " ind2=" "> | |
<subfield code="a">ei välittävää laitetta</subfield> | |
</datafield> | |
}; | |
declare function marc:field-490( | |
$series as element(isbnFormSeries)*, | |
$volume as element(isbnFormVolume)*, | |
$issn as element(ISSN)?) as element()? { | |
if (string-length($series)>2 and string-length($volume)>=1 and string-length($issn)>=1) then | |
<datafield tag="490" ind1="0" ind2=" "> | |
<subfield code="a">{concat(data($series),',')}</subfield> | |
<subfield code="v">{data($volume)}</subfield> | |
<subfield code="x">{data($issn)}</subfield> | |
</datafield> | |
else if (string-length($series)>2) then | |
<datafield tag="490" ind1="0" ind2=" "> | |
<subfield code="a">{data($series)}</subfield> | |
</datafield> | |
else() | |
}; | |
declare function marc:field-500() as element() { | |
<datafield tag="500" ind1=" " ind2=" "> | |
<subfield code="a">ENNAKKOTIET CIP/JYK</subfield> | |
</datafield> | |
}; | |
declare function marc:field-700($authors as node()*) as node()* { | |
for $author in $authors/author | |
let $subfield_e:= | |
if (string-length($author/@role)>2) then | |
<subfield code="e">{concat($author/@role,'.')}</subfield> | |
else() | |
return | |
if ($author/@surname) then | |
<datafield tag="700" ind1="1" ind2=" "> | |
<subfield code="a">{concat($author/@surname,', ',$author/@firstname,',')}</subfield> | |
<subfield code="c">ennakkotieto.</subfield> | |
{$subfield_e} | |
</datafield> | |
else() | |
}; | |
declare function marc:create-marcxml($record as node()) as node() { | |
let $authors:= | |
<authors> | |
{ | |
for $i in (1,2,3,4,5) | |
let $firstname:= $record/*[fn:node-name(.) = | |
xs:QName(concat('isbnFormAuthor',$i,'Firstname'))] | |
let $surname:= $record/*[fn:node-name(.) = | |
xs:QName(concat('isbnFormAuthor',$i,'Surname'))] | |
let $role:= $record/*[fn:node-name(.) = | |
xs:QName(concat('isbnFormAuthor',$i,'Role'))] | |
let $author_exists:=string-length(concat($firstname,$surname))>6 | |
return if ($author_exists) then | |
<author surname="{$surname}" firstname="{$firstname}" role="{$role}"/> | |
else() | |
} | |
</authors> | |
return | |
<record> | |
{marc:leader($record/isbnFormSeries)} | |
<controlfield tag="001">0000000</controlfield> | |
{marc:field-005()} | |
{marc:field-008($record/isbnFormPublishingYear,$record/isbnFormPublishingLang)} | |
{marc:field-020($record/isbnFormISBN, $record/isbnFormFormat)} | |
{marc:field-041($record/isbnFormLang)} | |
{marc:field-245($record/isbnFormTitle,$record/isbnFormSubtitle)} | |
{marc:field-100($authors/author[@role="author"][1])} | |
{marc:field-260($record/isbnFormPublishingHouse,$record/isbnFormPublishingYear)} | |
{marc:field-263($record/isbnFormPublishingYear)} | |
{marc:field-336()} | |
{marc:field-337()} | |
{marc:field-490($record/isbnFormSeries,$record/isbnFormVolume,$record/ISSN)} | |
{marc:field-500()} | |
{marc:field-700($authors)} | |
</record> | |
}; | |
declare function marc:create-marc($marcxml as node()) as xs:string { | |
let $file:= file:write('/tmp/temporary-marcxml.xml',$marcxml, map { "method" := "xml"}) | |
let $output:= | |
proc:execute('/usr/local/bin/yaz-marcdump', ('-i','marcxml', '-o','marc', '/tmp/temporary-marcxml.xml')) | |
return | |
if ($output/code eq '0') then | |
data($output//output) | |
else( | |
'Virhe MARC-muunnoksessa' | |
) | |
}; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment