[seiscomp, scanloc] Install, add .gitignore
This commit is contained in:
914
share/xml/0.11/quakeml_1.2__sc3ml_0.11.xsl
Normal file
914
share/xml/0.11/quakeml_1.2__sc3ml_0.11.xsl
Normal file
@ -0,0 +1,914 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!--
|
||||
QuakeML 1.2 to SCML (SeisComPML) 0.11 stylesheet converter
|
||||
|
||||
Author:
|
||||
EOST (École et Observatoire des Sciences de la Terre)
|
||||
Stephan Herrnkind <herrnkind@gempa.de>
|
||||
Copyright:
|
||||
The ObsPy Development Team (devs@obspy.org)
|
||||
License:
|
||||
GNU Lesser General Public License, Version 3
|
||||
(https://www.gnu.org/copyleft/lesser.html)
|
||||
|
||||
Usage
|
||||
=====
|
||||
|
||||
This stylesheet converts a QuakeML to a SCML document. It may be invoked using
|
||||
xalan or xsltproc:
|
||||
|
||||
xalan -in quakeml.xml -xsl quakeml_1.2__sc3ml_0.11.xsl -out sc3ml.xml
|
||||
xsltproc quakeml_1.2__sc3ml_0.11.xsl quakeml.xml > sc3ml.xml
|
||||
|
||||
Due to the QuakeML ID schema the public IDs used by QuakeML are rather long
|
||||
and may cause problems in SeisComP applications when displaying or processing
|
||||
them. Especially the slash causes problems, e.g., when an event ID is used on
|
||||
the command line or in a directory structure. To remove the ID prefix during
|
||||
the conversion you may use the ID_PREFIX parameter:
|
||||
|
||||
xalan -param ID_PREFIX "smi:org.gfz-potsdam.de/geofon/" -in quakeml.xml -xsl quakeml_1.2__sc3ml_0.12.xsl -out scml.xml
|
||||
xsltproc -stringparam ID_PREFIX smi:org.gfz-potsdam.de/geofon/ quakeml_1.2__sc3ml_0.11.xsl quakeml.xml > scml.xml
|
||||
|
||||
Other variable exist which control
|
||||
- the eventID format (BUILD_EVENT_ID),
|
||||
- the mapping of Magnitudes to Origins (GUESS_MAG_ORIGIN) or
|
||||
- the creation of unique ids (EVENT_INFO_ID)
|
||||
|
||||
|
||||
Profiles
|
||||
````````
|
||||
|
||||
The following table collects recommendated parameters setting for the QuakeML
|
||||
import from different agencies:
|
||||
|
||||
Agency ID_PREFIX BUILD_EVENT_ID GUESS_MAG_ORIGIN EVENT_INFO_ID
|
||||
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
|
||||
USGS quakeml:us.anss.org/ 2 3 1
|
||||
|
||||
|
||||
Transformation
|
||||
==============
|
||||
|
||||
QuakeML and SCML are quite similar schemas. Nevertheless some differences
|
||||
exist.
|
||||
|
||||
|
||||
ID restrictions
|
||||
```````````````
|
||||
|
||||
SCML does not enforce any particular ID restriction unlike QuakeML. It isn't
|
||||
a problem to convert from QuakeML to SCML. However, the QuakeML ID prefix may
|
||||
be removed during the conversion, see ID_PREFIX variable.
|
||||
|
||||
|
||||
Repositioning and creation of elements
|
||||
``````````````````````````````````````
|
||||
|
||||
QuakeML groups all elements under the event element where SCML places elements
|
||||
which might exist independent of an event, such as picks, amplitudes or origins
|
||||
directly under the EventParameters element. Furthermore SCML does not support
|
||||
magnitudes independent of an origin.
|
||||
|
||||
QuakeML SCML
|
||||
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
|
||||
<eventParameters> <EventParameters>
|
||||
<event>
|
||||
<pick/> <pick/>
|
||||
<amplitude/> <amplitude/>
|
||||
<reading/>
|
||||
<origin/> <origin>
|
||||
<stationMagnitude/> <stationMagnitude/>
|
||||
<magnitude/> <magnitude/>
|
||||
</origin>
|
||||
<focalMechanism/> <focalMechanism/>
|
||||
</event> <event/>
|
||||
</eventParameters> </EventParameters>
|
||||
|
||||
In SCML an event
|
||||
- uses Origin- and FocalMechanismReferences to associate Origins and
|
||||
FocalMechanisms,
|
||||
- Picks are associated via the Arrivals of an Origin and
|
||||
- Amplitudes are connected via StationMagnitudes of an Origin
|
||||
|
||||
Some elements are mandatory in SCML but aren't in QuakeML:
|
||||
- event/description/type
|
||||
- dataUsed/stationCount
|
||||
- dataUsed/componentCount
|
||||
- amplitude/type
|
||||
|
||||
|
||||
Renaming of nodes
|
||||
`````````````````
|
||||
|
||||
The following table lists the mapping of names between both schema:
|
||||
|
||||
Parent QuakeML name SCML name
|
||||
'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
|
||||
seiscomp eventParameters EventParameters
|
||||
arrival [value copied from fields weight
|
||||
below in order of listing]
|
||||
timeWeight timeUsed (bool)
|
||||
horizontalSlownessWeight horizontalSlownessUsed (bool)
|
||||
backazimuthWeight backazimuthUsed (bool)
|
||||
arrival takeoffAngle (RealQuantity) takeOffAngle (double)
|
||||
magnitude mag magnitude
|
||||
stationMagnitude mag magnitude
|
||||
amplitude genericAmplitude amplitude
|
||||
origin originUncertainty uncertainty
|
||||
momentTensor category method
|
||||
comment @id (attribute) id
|
||||
waveformID text() resourceURI
|
||||
|
||||
|
||||
Enumerations
|
||||
````````````
|
||||
|
||||
Both schema use enumerations. Numerous mappings are applied.
|
||||
|
||||
|
||||
Unit conversion
|
||||
```````````````
|
||||
|
||||
QuakeML uses meter for origin depth, origin uncertainty and confidence
|
||||
ellipsoid, SCML uses kilometer.
|
||||
|
||||
|
||||
Unmapped node
|
||||
`````````````
|
||||
|
||||
The following nodes can not be mapped to the SCML schema, thus their data is
|
||||
lost:
|
||||
|
||||
Parent Element lost
|
||||
''''''''''''''''''''''''''''''''''''''''''''
|
||||
amplitude evaluationStatus
|
||||
magnitude evaluationMode
|
||||
originUncertainty confidenceLevel
|
||||
arrival commment
|
||||
arrival horizontalSlownessWeight
|
||||
arrival backazimuthWeight
|
||||
origin region
|
||||
dataUsed longestPeriod
|
||||
momentTensor inversionType
|
||||
focalMechanism waveformID
|
||||
|
||||
|
||||
Nodes order
|
||||
```````````
|
||||
|
||||
Unlike SCML, QuakeML nodes can appear in any order. They must be reordered for
|
||||
SCML. Unnecessary attributes must also be removed.
|
||||
|
||||
Missing of mandatory elements - Shortcoming of QuakeML validation
|
||||
`````````````````````````````````````````````````````````````````
|
||||
|
||||
Some elements are marked as mandatory in QuakeML (minOccurs=1) but since they
|
||||
are defined in a xs:choice collection schema validators fail to detect the
|
||||
absence of such mandatory elements. E.g., it is possible to produce a valid
|
||||
QuakeML document containing an arrival without a phase definition.
|
||||
|
||||
|
||||
Change log
|
||||
==========
|
||||
|
||||
* 16.06.2021: Add ID_PREFIX parameter allowing to strip QuakeML ID prefix from
|
||||
publicIDs and references thereof.
|
||||
|
||||
* 22.06.2021: Add Z suffix to xs:dateTime values.
|
||||
|
||||
* 18.01.2023:
|
||||
- Add GUESS_MAG_ORIGIN switch allowing to map magnitudes to origins
|
||||
without an originID reference.
|
||||
- Add BUILD_EVENT_ID switch to construct event publicID from
|
||||
- last path component of the URI only or
|
||||
- by concatenating catalog:eventsource and catalog:eventid attribute as
|
||||
used, e.g., by USGS
|
||||
- In the absence of a stationSagnitude/waveformID the waveformID will be copied
|
||||
from the referenced amplitude if any.
|
||||
- Add EVENT_INFO_ID switch which creates unique publicIDs by appending the
|
||||
event publicID and event creation time.
|
||||
- Add value of '0' for unset dataUsed/stationCount|componentCount.
|
||||
- In the absence of the mandatory arrival/phase element phaseHint of the referenced
|
||||
pick is used. If neither a phaseHint is available the phase is set to an empty
|
||||
value.
|
||||
- Remove ID_PREFIX from comment/id and waveformID/resourceURI
|
||||
|
||||
* 26.07.2024:
|
||||
- Fix origin/confidenceEllipsoid conversion. The unit for
|
||||
'semiMajorAxisLength', 'semiMinorAxisLength' and
|
||||
'semiIntermediateAxisLength' is already meter and does not need a
|
||||
conversion.
|
||||
|
||||
-->
|
||||
<xsl:stylesheet version="1.0"
|
||||
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
|
||||
xmlns:xs="http://www.w3.org/2001/XMLSchema"
|
||||
xmlns:ext="http://exslt.org/common"
|
||||
xmlns="http://geofon.gfz-potsdam.de/ns/seiscomp3-schema/0.11"
|
||||
xmlns:qml="http://quakeml.org/xmlns/bed/1.2"
|
||||
xmlns:q="http://quakeml.org/xmlns/quakeml/1.2"
|
||||
xmlns:catalog="http://anss.org/xmlns/catalog/0.1"
|
||||
exclude-result-prefixes="xsl xs ext q qml catalog">
|
||||
<xsl:output method="xml" encoding="UTF-8" indent="yes"/>
|
||||
<xsl:strip-space elements="*"/>
|
||||
|
||||
<!--
|
||||
Define parameters which may be passed to this script.
|
||||
-->
|
||||
|
||||
<!-- Prefix to be removed from any publicID -->
|
||||
<xsl:param name="ID_PREFIX" select="'smi:org.gfz-potsdam.de/geofon/'"/>
|
||||
|
||||
<!-- PublicID representing an empty value -->
|
||||
<xsl:param name="ID_PREFIX_NA" select="concat($ID_PREFIX, 'NA')"/>
|
||||
|
||||
<!-- In QuakeML a magnitude references to its origin via the originID
|
||||
element. Some catalogs don't set this element. The GUESS_MAG_ORIGIN
|
||||
variable represents a bit mask with certain guessing strategies:
|
||||
0: Don't guess the origin.
|
||||
1: Single origin. If the document contains only one origin all
|
||||
magnitudes and stationMagnitudes without an originID reference will
|
||||
be mapped to the single origin.
|
||||
2: Preferred origin. Map magnitutes and stationMagnitudes without an
|
||||
origin reference to the preferredOrigin. -->
|
||||
<xsl:param name="GUESS_MAG_ORIGIN" select="0"/>
|
||||
|
||||
<!-- Special rules for the contruction of the event publicID:
|
||||
0: Use ID as is but remove ID_PREFIX as done with any other publicIDs
|
||||
1: Extract only the last path component of the URI
|
||||
2: Combine event attributes catalog:eventsource and catalog:eventid.
|
||||
E.g., this option is suitable for the USGS QuakeML flavor.
|
||||
-->
|
||||
<xsl:param name="BUILD_EVENT_ID" select="0"/>
|
||||
|
||||
<!-- Make all public IDs unique by appending event publicID and the event
|
||||
creation time -->
|
||||
<xsl:param name="EVENT_INFO_ID" select="0"/>
|
||||
|
||||
<!-- Define some global variables -->
|
||||
<xsl:variable name="version" select="'0.11'"/>
|
||||
<xsl:variable name="schema" select="document('sc3ml_0.11.xsd')"/>
|
||||
<xsl:variable name="PID" select="'publicID'"/>
|
||||
|
||||
<!-- Define key to remove duplicates-->
|
||||
<xsl:key name="pick_key" match="qml:pick" use="@publicID"/>
|
||||
<xsl:key name="amplitude_key" match="qml:amplitude" use="@publicID"/>
|
||||
<xsl:key name="origin_key" match="qml:origin" use="@publicID"/>
|
||||
<xsl:key name="focalMechanism_key" match="qml:focalMechanism" use="@publicID"/>
|
||||
|
||||
|
||||
<!--
|
||||
***************************************************************************
|
||||
Utility functions
|
||||
***************************************************************************
|
||||
-->
|
||||
|
||||
<!-- Reverse seach $delimiter in $string. 'tokenize' only available with
|
||||
XSLT 2.0 -->
|
||||
<xsl:template name="substring-after-last">
|
||||
<xsl:param name="string"/>
|
||||
<xsl:param name="delimiter"/>
|
||||
|
||||
<!-- Extract the string which comes after the first occurence -->
|
||||
<xsl:variable name="remainder" select="substring-after($string, $delimiter)"/>
|
||||
|
||||
<xsl:choose>
|
||||
<!-- If it still contains the search string the recursively process -->
|
||||
<xsl:when test="$delimiter and contains($remainder, $delimiter)">
|
||||
<xsl:call-template name="substring-after-last">
|
||||
<xsl:with-param name="string" select="$remainder"/>
|
||||
<xsl:with-param name="delimiter" select="$delimiter"/>
|
||||
</xsl:call-template>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>
|
||||
<xsl:value-of select="$remainder"/>
|
||||
</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:template>
|
||||
|
||||
<!--
|
||||
***************************************************************************
|
||||
Move/create nodes
|
||||
***************************************************************************
|
||||
-->
|
||||
|
||||
<!-- Default match: Map node 1:1 -->
|
||||
<xsl:template match="*">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<xsl:apply-templates select="node()"/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Starting point: Match the root node and select the EventParameters
|
||||
node -->
|
||||
<xsl:template match="/">
|
||||
<!-- Write a disordered SCML in this variable. It will be ordered in
|
||||
a second run. -->
|
||||
<xsl:variable name="disordered">
|
||||
<xsl:for-each select="./q:quakeml/qml:eventParameters">
|
||||
<EventParameters>
|
||||
<xsl:attribute name="{$PID}">
|
||||
<xsl:call-template name="removeIDPrefix">
|
||||
<xsl:with-param name="id" select="@publicID"/>
|
||||
</xsl:call-template>
|
||||
</xsl:attribute>
|
||||
<xsl:apply-templates select="qml:event"/>
|
||||
</EventParameters>
|
||||
</xsl:for-each>
|
||||
</xsl:variable>
|
||||
|
||||
<!-- Reorder nodes -->
|
||||
<seiscomp version="{$version}">
|
||||
<xsl:apply-templates select="ext:node-set($disordered)" mode="reorder"/>
|
||||
</seiscomp>
|
||||
</xsl:template>
|
||||
|
||||
<xsl:template match="qml:event">
|
||||
<!-- Create event node -->
|
||||
<xsl:element name="{local-name()}">
|
||||
<!-- Special rules for the construction of the event publicID -->
|
||||
<xsl:attribute name="{$PID}">
|
||||
<xsl:call-template name="eventID">
|
||||
<xsl:with-param name="event" select="current()"/>
|
||||
</xsl:call-template>
|
||||
</xsl:attribute>
|
||||
<xsl:apply-templates/>
|
||||
|
||||
<!-- Create origin references -->
|
||||
<xsl:for-each select="qml:origin[count(. | key('origin_key', @publicID)[1]) = 1]">
|
||||
<xsl:element name="originReference">
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="@publicID"/>
|
||||
</xsl:call-template>
|
||||
</xsl:element>
|
||||
</xsl:for-each>
|
||||
|
||||
<!-- Create focal mechanism references -->
|
||||
<xsl:for-each select="qml:focalMechanism[count(. | key('focalMechanism_key', @publicID)[1]) = 1]">
|
||||
<xsl:element name="focalMechanismReference">
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="@publicID"/>
|
||||
</xsl:call-template>
|
||||
</xsl:element>
|
||||
</xsl:for-each>
|
||||
</xsl:element>
|
||||
|
||||
<!-- Copy picks and remove duplicates -->
|
||||
<xsl:for-each select="qml:pick[count(. | key('pick_key', @publicID)[1]) = 1]">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:for-each>
|
||||
|
||||
<!-- Copy amplitudes and remove duplicates -->
|
||||
<xsl:for-each select="qml:amplitude[count(. | key('amplitude_key', @publicID)[1]) = 1]">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<xsl:if test="not(qml:type)">
|
||||
<xsl:element name="type"/>
|
||||
</xsl:if>
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:for-each>
|
||||
|
||||
<!-- Definition of fallback origin if GUESS_MAG_ORIGIN is set to a
|
||||
value greater than 0. -->
|
||||
<xsl:variable name="fallback_origin_id">
|
||||
<xsl:choose>
|
||||
<!-- Single origin -->
|
||||
<xsl:when test="floor($GUESS_MAG_ORIGIN div 1) mod 2 = 1 and count(qml:origin) = 1">
|
||||
<xsl:value-of select="qml:origin[1]/@publicID"/>
|
||||
</xsl:when>
|
||||
<!-- Preferred origin -->
|
||||
<xsl:when test="floor($GUESS_MAG_ORIGIN div 2) mod 2 = 1">
|
||||
<xsl:value-of select="qml:preferredOriginID/text()"/>
|
||||
</xsl:when>
|
||||
</xsl:choose>
|
||||
</xsl:variable>
|
||||
|
||||
<!-- Copy origins and remove duplicates -->
|
||||
<xsl:for-each select="qml:origin[count(. | key('origin_key', @publicID)[1]) = 1]">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
|
||||
<!-- Copy magnitudes -->
|
||||
<xsl:for-each select="../qml:magnitude[qml:originID/text()=current()/@publicID or (
|
||||
not(qml:originID) and current()/@publicID = $fallback_origin_id)]">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:for-each>
|
||||
|
||||
<!-- Copy stations magnitudes -->
|
||||
<xsl:for-each select="../qml:stationMagnitude[qml:originID/text()=current()/@publicID or (
|
||||
not(qml:originID) and current()/@publicID = $fallback_origin_id)]">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<xsl:apply-templates/>
|
||||
|
||||
<!-- use waveformID of referenced amplitude as fallback -->
|
||||
<xsl:if test="not(qml:waveformID)">
|
||||
<xsl:apply-templates select="../qml:amplitude[current()/qml:amplitudeID/text()=@publicID][1]/qml:waveformID"/>
|
||||
</xsl:if>
|
||||
</xsl:element>
|
||||
</xsl:for-each>
|
||||
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:for-each>
|
||||
|
||||
<!-- Copy focal mechanisms and remove duplicates -->
|
||||
<xsl:for-each select="qml:focalMechanism[count(. | key('focalMechanism_key', @publicID)[1]) = 1]">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:for-each>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Create mandatory element event/description/type -->
|
||||
<xsl:template match="qml:event/qml:description">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:if test="not(qml:type)">
|
||||
<xsl:element name="type">region name</xsl:element>
|
||||
</xsl:if>
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Create mandatory elements dataUsed/stationCount and
|
||||
dataUsed/componentCount -->
|
||||
<xsl:template match="qml:dataUsed">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:if test="not(qml:stationCount)">
|
||||
<xsl:element name="stationCount">
|
||||
<xsl:value-of select="0"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
<xsl:if test="not(qml:componentCount)">
|
||||
<xsl:element name="componentCount">
|
||||
<xsl:value-of select="0"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Create mandatory element arrival/phase -->
|
||||
<xsl:template match="qml:arrival">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:if test="not(qml:phase)">
|
||||
<xsl:element name="phase">
|
||||
<xsl:value-of select="../../qml:pick[current()/qml:pickID/text()=@publicID]/qml:phaseHint/text()"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
|
||||
<!--
|
||||
***************************************************************************
|
||||
Rename nodes/attributes
|
||||
***************************************************************************
|
||||
-->
|
||||
|
||||
<!-- Manage arrival/weight -->
|
||||
<xsl:template match="qml:arrival/qml:timeWeight">
|
||||
<xsl:element name="weight">
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
<xsl:element name="timeUsed">true</xsl:element>
|
||||
</xsl:template>
|
||||
<xsl:template match="qml:arrival/qml:horizontalSlownessWeight">
|
||||
<xsl:if test="not(../qml:timeWeight)">
|
||||
<xsl:element name="weight">
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
<xsl:element name="horizontalSlownessUsed">true</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:template>
|
||||
<xsl:template match="qml:arrival/qml:backazimuthWeight">
|
||||
<xsl:if test="not(../qml:timeWeight) and not(../qml:horizontalSlownessWeight)">
|
||||
<xsl:element name="weight">
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
<xsl:element name="backazimuthUsed">true</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:template>
|
||||
|
||||
<!-- arrival/takeoffAngle -> arrival/takeOffAngle -->
|
||||
<xsl:template match="qml:arrival/qml:takeoffAngle">
|
||||
<xsl:element name="takeOffAngle">
|
||||
<xsl:value-of select="qml:value"/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- magnitude/mag -> magnitude/magnitude -->
|
||||
<!-- stationMagnitude/mag -> stationMagnitude/magnitude -->
|
||||
<xsl:template match="qml:magnitude/qml:mag
|
||||
| qml:stationMagnitude/qml:mag">
|
||||
<xsl:element name="magnitude">
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- amplitude/genericAmplitutde -> amplitude/amplitude -->
|
||||
<xsl:template match="qml:amplitude/qml:genericAmplitude">
|
||||
<xsl:element name="amplitude">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- origin/originUncertainty -> origin/uncertainty -->
|
||||
<xsl:template match="qml:origin/qml:originUncertainty">
|
||||
<xsl:element name="uncertainty">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- momentTensor/category -> momentTensor/method -->
|
||||
<xsl:template match="qml:momentTensor/qml:category">
|
||||
<xsl:element name="method">
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- comment/@id -> comment/id -->
|
||||
<xsl:template match="qml:comment">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:if test="@id != ''">
|
||||
<xsl:element name="id">
|
||||
<xsl:call-template name="removeIDPrefix">
|
||||
<xsl:with-param name="id" select="@id"/>
|
||||
</xsl:call-template>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- waveformID/text() -> waveformID/resourceURI -->
|
||||
<xsl:template match="qml:waveformID">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<xsl:if test="current() != ''">
|
||||
<xsl:element name="resourceURI">
|
||||
<xsl:call-template name="removeIDPrefix">
|
||||
<xsl:with-param name="id" select="."/>
|
||||
</xsl:call-template>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!--
|
||||
***************************************************************************
|
||||
Enumeration mapping
|
||||
***************************************************************************
|
||||
-->
|
||||
|
||||
<xsl:template match="qml:event/qml:type">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:variable name="v" select="."/>
|
||||
<xsl:choose>
|
||||
<xsl:when test="$v='other event'">other</xsl:when>
|
||||
<xsl:otherwise><xsl:value-of select="$v"/></xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<xsl:template match="qml:origin/qml:depthType">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:variable name="v" select="."/>
|
||||
<xsl:choose>
|
||||
<xsl:when test="$v='constrained by depth and direct phases'">other</xsl:when>
|
||||
<xsl:otherwise><xsl:value-of select="$v"/></xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<xsl:template match="qml:momentTensor/qml:dataUsed/qml:waveType">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:variable name="v" select="."/>
|
||||
<xsl:choose>
|
||||
<xsl:when test="$v='P waves'">P body waves</xsl:when>
|
||||
<xsl:when test="$v='mantle waves'">long-period mantle waves</xsl:when>
|
||||
<xsl:when test="$v='combined'">unknown</xsl:when>
|
||||
<xsl:otherwise><xsl:value-of select="$v"/></xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!--
|
||||
***************************************************************************
|
||||
Unit conversion
|
||||
***************************************************************************
|
||||
-->
|
||||
|
||||
<!-- Origin depth, SCML uses kilometer, QuakeML meter -->
|
||||
<xsl:template match="qml:origin/qml:depth/qml:value
|
||||
| qml:origin/qml:depth/qml:uncertainty
|
||||
| qml:origin/qml:depth/qml:lowerUncertainty
|
||||
| qml:origin/qml:depth/qml:upperUncertainty
|
||||
| qml:origin/qml:originUncertainty/qml:horizontalUncertainty
|
||||
| qml:origin/qml:originUncertainty/qml:minHorizontalUncertainty
|
||||
| qml:origin/qml:originUncertainty/qml:maxHorizontalUncertainty">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:value-of select="current() div 1000"/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!--
|
||||
***************************************************************************
|
||||
Time conversion
|
||||
***************************************************************************
|
||||
-->
|
||||
|
||||
<!-- SeisComP < 5 requires date time values to end on Z -->
|
||||
<xsl:template match="qml:time/qml:value
|
||||
| qml:scalingTime/qml:value
|
||||
| qml:timeWindow/qml:reference
|
||||
| qml:creationTime">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:variable name="v" select="current()"/>
|
||||
<xsl:choose>
|
||||
<xsl:when test="substring($v, string-length($v))='Z'">
|
||||
<xsl:value-of select="$v"/>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>
|
||||
<xsl:value-of select="concat($v, 'Z')"/>
|
||||
</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!--
|
||||
***************************************************************************
|
||||
Delete moved/unmapped nodes
|
||||
***************************************************************************
|
||||
-->
|
||||
|
||||
<xsl:template match="qml:pick"/>
|
||||
<xsl:template match="qml:amplitude"/>
|
||||
<xsl:template match="qml:origin"/>
|
||||
<xsl:template match="qml:magnitude"/>
|
||||
<xsl:template match="qml:stationMagnitude"/>
|
||||
<xsl:template match="qml:focalMechanism"/>
|
||||
<xsl:template match="qml:amplitude/qml:category"/>
|
||||
<xsl:template match="qml:amplitude/qml:evaluationStatus"/>
|
||||
<xsl:template match="qml:magnitude/qml:evaluationMode"/>
|
||||
<xsl:template match="qml:originUncertainty/qml:confidenceLevel"/>
|
||||
<xsl:template match="qml:arrival/qml:comment"/>
|
||||
<xsl:template match="qml:origin/qml:region"/>
|
||||
<xsl:template match="qml:dataUsed/qml:longestPeriod"/>
|
||||
<xsl:template match="qml:momentTensor/qml:inversionType"/>
|
||||
<xsl:template match="qml:focalMechanism/qml:waveformID"/>
|
||||
|
||||
<!--
|
||||
***************************************************************************
|
||||
Reorder element nodes
|
||||
***************************************************************************
|
||||
-->
|
||||
|
||||
<xsl:template match="*" mode="reorder">
|
||||
<!-- Detect complexType from node name -->
|
||||
<xsl:variable name="name">
|
||||
<xsl:variable name="v" select="local-name()"/>
|
||||
<xsl:variable name="p" select="local-name(..)"/>
|
||||
<xsl:choose>
|
||||
<xsl:when test="$v='scalingTime'">TimeQuantity</xsl:when>
|
||||
<xsl:when test="$v='time'">TimeQuantity</xsl:when>
|
||||
<xsl:when test="$v='creationInfo'">CreationInfo</xsl:when>
|
||||
<xsl:when test="$p='event' and $v='description'">EventDescription</xsl:when>
|
||||
<xsl:when test="$v='comment'">Comment</xsl:when>
|
||||
<xsl:when test="$p='tAxis' and $v='azimuth'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$p='pAxis' and $v='azimuth'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$p='nAxis' and $v='azimuth'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$v='plunge'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$v='length'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$v='second'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$v='Mrr'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$v='Mtt'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$v='Mpp'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$v='Mrt'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$v='Mrp'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$v='Mtp'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$v='strike'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$p='nodalPlane1' and $v='dip'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$p='nodalPlane2' and $v='dip'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$v='rake'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$v='scalarMoment'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$p='amplitude' and $v='amplitude'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$v='period'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$p='magnitude' and $v='magnitude'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$p='stationMagnitude' and $v='magnitude'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$v='horizontalSlowness'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$v='backazimuth'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$p='origin' and $v='latitude'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$p='origin' and $v='longitude'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$p='origin' and $v='depth'">RealQuantity</xsl:when>
|
||||
<xsl:when test="$v='year'">IntegerQuantity</xsl:when>
|
||||
<xsl:when test="$v='month'">IntegerQuantity</xsl:when>
|
||||
<xsl:when test="$v='day'">IntegerQuantity</xsl:when>
|
||||
<xsl:when test="$v='hour'">IntegerQuantity</xsl:when>
|
||||
<xsl:when test="$v='minute'">IntegerQuantity</xsl:when>
|
||||
<xsl:when test="$v='tAxis'">Axis</xsl:when>
|
||||
<xsl:when test="$v='pAxis'">Axis</xsl:when>
|
||||
<xsl:when test="$v='nAxis'">Axis</xsl:when>
|
||||
<xsl:when test="$v='principalAxes'">PrincipalAxes</xsl:when>
|
||||
<xsl:when test="$v='dataUsed'">DataUsed</xsl:when>
|
||||
<xsl:when test="$v='compositeTime'">CompositeTime</xsl:when>
|
||||
<xsl:when test="$v='tensor'">Tensor</xsl:when>
|
||||
<xsl:when test="$v='quality'">OriginQuality</xsl:when>
|
||||
<xsl:when test="$v='nodalPlane1'">NodalPlane</xsl:when>
|
||||
<xsl:when test="$v='nodalPlane2'">NodalPlane</xsl:when>
|
||||
<xsl:when test="$v='timeWindow'">TimeWindow</xsl:when>
|
||||
<xsl:when test="$v='waveformID'">WaveformStreamID</xsl:when>
|
||||
<xsl:when test="$v='sourceTimeFunction'">SourceTimeFunction</xsl:when>
|
||||
<xsl:when test="$v='nodalPlanes'">NodalPlanes</xsl:when>
|
||||
<xsl:when test="$v='confidenceEllipsoid'">ConfidenceEllipsoid</xsl:when>
|
||||
<xsl:when test="$v='reading'">Reading</xsl:when>
|
||||
<xsl:when test="$v='component'">MomentTensorComponentContribution</xsl:when>
|
||||
<xsl:when test="$v='stationMomentTensorContribution'">MomentTensorStationContribution</xsl:when>
|
||||
<xsl:when test="$v='phaseSetting'">MomentTensorPhaseSetting</xsl:when>
|
||||
<xsl:when test="$v='momentTensor'">MomentTensor</xsl:when>
|
||||
<xsl:when test="$v='focalMechanism'">FocalMechanism</xsl:when>
|
||||
<xsl:when test="$p='EventParameters' and $v='amplitude'">Amplitude</xsl:when>
|
||||
<xsl:when test="$v='stationMagnitudeContribution'">StationMagnitudeContribution</xsl:when>
|
||||
<xsl:when test="$p='origin' and $v='magnitude'">Magnitude</xsl:when>
|
||||
<xsl:when test="$v='stationMagnitude'">StationMagnitude</xsl:when>
|
||||
<xsl:when test="$v='pick'">Pick</xsl:when>
|
||||
<xsl:when test="$v='event'">Event</xsl:when>
|
||||
<xsl:when test="$p='origin' and $v='uncertainty'">OriginUncertainty</xsl:when>
|
||||
<xsl:when test="$v='arrival'">Arrival</xsl:when>
|
||||
<xsl:when test="$v='origin'">Origin</xsl:when>
|
||||
<xsl:otherwise/>
|
||||
</xsl:choose>
|
||||
</xsl:variable>
|
||||
<xsl:variable name="current" select="."/>
|
||||
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:choose>
|
||||
<xsl:when test="$name=''">
|
||||
<!-- Not a complexType, don't reorder -->
|
||||
<xsl:apply-templates select="node()" mode="reorder"/>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>
|
||||
<!-- This node is a complexType. -->
|
||||
<!-- Only copy allowed attributes -->
|
||||
<xsl:for-each select="$schema//xs:complexType[@name=$name]
|
||||
/xs:attribute/@name">
|
||||
<xsl:copy-of select="$current/@*[local-name()=current()]"/>
|
||||
</xsl:for-each>
|
||||
<!-- Reorder nodes according to the XSD -->
|
||||
<xsl:for-each select="$schema//xs:complexType[@name=$name]
|
||||
/xs:sequence/xs:element/@name">
|
||||
<xsl:apply-templates select="$current/*[local-name()=current()]"
|
||||
mode="reorder"/>
|
||||
</xsl:for-each>
|
||||
</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Converts a publicID -->
|
||||
<xsl:template name="convertID">
|
||||
<xsl:param name="id"/>
|
||||
<xsl:variable name="res">
|
||||
<xsl:call-template name="removeIDPrefix">
|
||||
<xsl:with-param name="id" select="$id"/>
|
||||
</xsl:call-template>
|
||||
</xsl:variable>
|
||||
<xsl:choose>
|
||||
<xsl:when test="$EVENT_INFO_ID != 0">
|
||||
<xsl:call-template name="eventInfoID">
|
||||
<xsl:with-param name="id" select="$res"/>
|
||||
</xsl:call-template>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>
|
||||
<xsl:value-of select="$res"/>
|
||||
</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Removes ID_PREFIX, if the remainder is 'NA' an empty string is returned -->
|
||||
<xsl:template name="removeIDPrefix">
|
||||
<xsl:param name="id"/>
|
||||
<xsl:choose>
|
||||
<xsl:when test="$id=$ID_PREFIX_NA">
|
||||
<xsl:value-of select="''"/>
|
||||
</xsl:when>
|
||||
<xsl:when test="starts-with($id, $ID_PREFIX)">
|
||||
<xsl:value-of select="substring-after($id, $ID_PREFIX)"/>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>
|
||||
<xsl:value-of select="$id"/>
|
||||
</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Special rules for the construction of the event publicID -->
|
||||
<xsl:template name="eventID">
|
||||
<xsl:param name="event"/>
|
||||
<xsl:choose>
|
||||
<!-- Use last id path component -->
|
||||
<xsl:when test="$BUILD_EVENT_ID = 1">
|
||||
<xsl:call-template name="substring-after-last">
|
||||
<xsl:with-param name="string" select="$event/@publicID"/>
|
||||
<xsl:with-param name="delimiter" select="'/'"/>
|
||||
</xsl:call-template>
|
||||
</xsl:when>
|
||||
<!-- Use catalog:eventsource and catalog:eventid -->
|
||||
<xsl:when test="$BUILD_EVENT_ID = 2">
|
||||
<xsl:value-of select="concat($event/@catalog:eventsource, $event/@catalog:eventid)"/>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>
|
||||
<xsl:call-template name="removeIDPrefix">
|
||||
<xsl:with-param name="id" select="$event/@publicID"/>
|
||||
</xsl:call-template>
|
||||
</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Adds eventID and event creation time to id parameter -->
|
||||
<xsl:template name="eventInfoID">
|
||||
<xsl:param name="id"/>
|
||||
<xsl:variable name="event" select="ancestor::*[last()-2]"/>
|
||||
<xsl:variable name="eventID">
|
||||
<xsl:call-template name="eventID">
|
||||
<xsl:with-param name="event" select="$event"/>
|
||||
</xsl:call-template>
|
||||
</xsl:variable>
|
||||
<xsl:value-of select="concat($id, '/', $eventID, '/', $event/qml:creationInfo/qml:creationTime)"/>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Remove ID_PREFIX from publicID attributes -->
|
||||
<xsl:template match="@publicID">
|
||||
<xsl:variable name="id">
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="current()"/>
|
||||
</xsl:call-template>
|
||||
</xsl:variable>
|
||||
<xsl:if test="$id != ''">
|
||||
<xsl:attribute name="{$PID}">
|
||||
<xsl:value-of select="$id"/>
|
||||
</xsl:attribute>
|
||||
</xsl:if>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Generic template for all remaining attributes -->
|
||||
<xsl:template match="@*">
|
||||
<xsl:copy-of select="."/>
|
||||
</xsl:template>
|
||||
|
||||
<!-- ID nodes which must be stripped from ID_PREFIX -->
|
||||
<xsl:template match="qml:agencyURI
|
||||
| qml:authorURI
|
||||
| qml:greensFunctionID
|
||||
| qml:filterID
|
||||
| qml:methodID
|
||||
| qml:earthModelID
|
||||
| qml:referenceSystemID
|
||||
| qml:slownessMethodID">
|
||||
<xsl:variable name="id">
|
||||
<xsl:call-template name="removeIDPrefix">
|
||||
<xsl:with-param name="id" select="string(.)"/>
|
||||
</xsl:call-template>
|
||||
</xsl:variable>
|
||||
<xsl:if test="$id != ''">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:value-of select="$id"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:template>
|
||||
|
||||
<!-- ID nodes referencing public objects: Remove ID_PREFIX and optionally ensure ID uniqueness. -->
|
||||
<xsl:template match="qml:derivedOriginID
|
||||
| qml:momentMagnitudeID
|
||||
| qml:triggeringOriginID
|
||||
| qml:pickID
|
||||
| qml:stationMagnitudeID
|
||||
| qml:originID
|
||||
| qml:amplitudeID
|
||||
| qml:preferredOriginID
|
||||
| qml:preferredMagnitudeID
|
||||
| qml:preferredFocalMechanismID">
|
||||
<xsl:variable name="id">
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="string(.)"/>
|
||||
</xsl:call-template>
|
||||
</xsl:variable>
|
||||
<xsl:if test="$id != ''">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:value-of select="$id"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:template>
|
||||
|
||||
</xsl:stylesheet>
|
1282
share/xml/0.11/sc3ml_0.11.xsd
Normal file
1282
share/xml/0.11/sc3ml_0.11.xsd
Normal file
File diff suppressed because it is too large
Load Diff
621
share/xml/0.11/sc3ml_0.11__quakeml_1.2-RT.xsl
Normal file
621
share/xml/0.11/sc3ml_0.11__quakeml_1.2-RT.xsl
Normal file
@ -0,0 +1,621 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!-- **********************************************************************
|
||||
* Copyright (C) 2017 by gempa GmbH
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as
|
||||
* published by the Free Software Foundation, version 3.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but
|
||||
* WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Lesser Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*
|
||||
* SC3ML 0.11 to QuakeML 1.2 RT stylesheet converter
|
||||
* Author : Stephan Herrnkind
|
||||
* Email : stephan.herrnkind@gempa.de
|
||||
* Version : 2017.342.01
|
||||
*
|
||||
* ================
|
||||
* Usage
|
||||
* ================
|
||||
*
|
||||
* This stylesheet converts a SC3ML to a QuakeML-RT document. It may be
|
||||
* invoked e.g. using xalan or xsltproc:
|
||||
*
|
||||
* xalan -in sc3ml.xml -xsl sc3ml_0.11__quakeml_1.2-RT.xsl -out quakeml.xml
|
||||
* xsltproc -o quakeml.xml sc3ml_0.11__quakeml_1.2-RT.xsl sc3ml.xml
|
||||
*
|
||||
* You can also modify the default ID prefix with the reverse DNS name of your
|
||||
* institute by setting the ID_PREFIX param:
|
||||
*
|
||||
* xalan -param ID_PREFIX "'smi:org.gfz-potsdam.de/geofon/'" -in sc3ml.xml -xsl sc3ml_0.11__quakeml_1.2-RT.xsl -out quakeml.xml
|
||||
* xsltproc -stringparam ID_PREFIX smi:org.gfz-potsdam.de/geofon/ -o quakeml.xml sc3ml_0.11__quakeml_1.2-RT.xsl sc3ml.xml
|
||||
*
|
||||
* ================
|
||||
* Transformation
|
||||
* ================
|
||||
*
|
||||
* QuakeML and SC3ML are quite similar schemas. Nevertheless some differences
|
||||
* exist:
|
||||
*
|
||||
* - IDs : SC3ML does not enforce any particular ID restriction. An ID in
|
||||
* SC3ML has no semantic, it simply must be unique. Hence QuakeML uses ID
|
||||
* restrictions, a conversion of a SC3ML to a QuakeML ID must be performed:
|
||||
* 'sc3id' -> 'smi:org.gfz-potsdam.de/geofon/'. If no SC3ML ID is available
|
||||
* but QuakeML enforces one, a static ID value of 'NA' is used.
|
||||
* If the ID starts with `smi:` or `quakeml:`, the ID is considered valid
|
||||
* and let untouched. This can lead to an invalid generated file but avoid
|
||||
* to always modify IDs, especially when converting several times.
|
||||
* - Repositioning of 'magnitude' and 'stationMagnitude' nodes : Whereas SC3ML
|
||||
* places these nodes under the 'origin' element, QuakeML-RT expects them on
|
||||
* the same level as the 'origin' element. When moving these nodes the
|
||||
* publicID of the parent 'origin' is copied to the 'originID' child node of
|
||||
* the magnitude nodes (except an originID was specified in the SC3ML
|
||||
* sources nodes).
|
||||
*
|
||||
* <EventParameters> <eventParameters>
|
||||
* <origin publicID="foo"> <origin publicID="smi:org.gfz-potsdam.de/geofon/foo"/>
|
||||
* <stationMagnitude/> <stationMagnitude>
|
||||
* <originID>smi:org.gfz-potsdam.de/geofon/foo</originID>
|
||||
* </stationMagnitude>
|
||||
* <magnitude> <magnitude>
|
||||
* <originID>bar</originID> <originID>smi:org.gfz-potsdam.de/geofon/bar</originID>
|
||||
* </magnitude> </magnitude>
|
||||
* </EventParameters> </eventParameters>
|
||||
*
|
||||
* - An 'event' in SC3ML and QuakeML-RT refers to its origins via
|
||||
* 'originReference' elements. Since in SC3ML 'magnitude' elements are
|
||||
* children of a 'origin' a connection of events and origins can be made.
|
||||
* For the same mapping QuakeML-RT uses 'magnitudeReference' elements.
|
||||
*
|
||||
* - Renaming of nodes: The following table lists the mapping of names between
|
||||
* both schema:
|
||||
*
|
||||
* Parent (SC3) SC3 name QuakeML name
|
||||
* """""""""""""""""""""""""""""""""""""""""""""""""""""""
|
||||
* seiscomp EventParameters eventParameters
|
||||
* arrival weight [copied to following fields if true]
|
||||
* timeUsed timeWeight
|
||||
* horizontalSlownessUsed horizontalSlownessWeight
|
||||
* backazimuthUsed backazimuthWeight
|
||||
* takeOffAngle takeoffAngle
|
||||
* magnitude magnitude mag
|
||||
* stationMagnitude magnitude mag
|
||||
* amplitude amplitude genericAmplitude
|
||||
* origin uncertainty originUncertainty
|
||||
* momentTensor method category
|
||||
* waveformID resourceURI CDATA
|
||||
* comment id id (attribute)
|
||||
*
|
||||
* - Enumerations: Both schema use enumerations. Numerous mappings are applied.
|
||||
*
|
||||
* - Unit conversion: SC3ML uses kilometer for origin depth and origin
|
||||
* uncertainty, QuakeML uses meter
|
||||
*
|
||||
* - Unmapped nodes: The following nodes can not be mapped to the QuakeML
|
||||
* schema, thus their data is lost:
|
||||
*
|
||||
* Parent Element lost
|
||||
* """""""""""""""""""""""""""""""""""""""""""""""""""""""""""
|
||||
* creationInfo modificationTime
|
||||
* momentTensor method
|
||||
* stationMomentTensorContribution
|
||||
* status
|
||||
* cmtName
|
||||
* cmtVersion
|
||||
* phaseSetting
|
||||
* stationMagnitude passedQC
|
||||
* eventParameters reading
|
||||
* comment start
|
||||
* comment end
|
||||
* RealQuantity pdf
|
||||
* TimeQuality pdf
|
||||
*
|
||||
* - Mandatory nodes: The following nodes is mandatory in QuakeML but not in
|
||||
* SC3ML:
|
||||
*
|
||||
* Parent Mandatory element
|
||||
* """"""""""""""""""""""""""""""""""""""""""""""""""""""""""
|
||||
* Amplitude genericAmplitude
|
||||
* StationMagnitude originID
|
||||
*
|
||||
* - Restriction of data size: QuakeML restricts string length of some
|
||||
* elements. This length restriction is _NOT_ enforced by this
|
||||
* stylesheet to prevent data loss. As a consequence QuakeML files
|
||||
* generated by this XSLT may not validate because of these
|
||||
* restrictions.
|
||||
*
|
||||
* ================
|
||||
* Change log
|
||||
* ================
|
||||
*
|
||||
* * 08.09.2014: Fixed typo in event type conversion (meteo[r] impact)
|
||||
*
|
||||
* * 25.08.2014: Applied part of the patch proposed by Philipp Kaestli on
|
||||
* seiscomp-l@gfz-potsdam.de
|
||||
* - use public id of parent origin if origin id propertery of magnitude
|
||||
* and station magnitude elements is unset
|
||||
* - fixed takeOffAngle conversion vom real (SC3ML) to RealQuantity
|
||||
* (QuakeML)
|
||||
*
|
||||
* * 04.07.2016: Version bump. No modification here, SC3 datamodel was updated
|
||||
* on the inventory side.
|
||||
*
|
||||
* * 28.11.2016: Version bump. No modification here, SC3 datamodel was updated
|
||||
* on the inventory side.
|
||||
*
|
||||
* * 28.06.2017: Changed license from GPL to LGPL
|
||||
*
|
||||
* * 08.08.2017: Added some fixes to use this XSLT in ObsPy
|
||||
* - Change ID_PREFIX variable to a param
|
||||
* - Do not copy Amplitude if amplitude/amplitude doesn't existing
|
||||
* - focalMechanism/evaluationMode and focalMechanism/evaluationStatus were
|
||||
* not copied but can actually be mapped to the QuakeML schema
|
||||
* - Some event/type enumeration was mapped to `other` instead of
|
||||
* `other event`
|
||||
* - Fix origin uncertainty and confidence ellispoid units
|
||||
* - Rename momentTensor/method to momentTensor/category
|
||||
* - Fix amplitude/unit (enumeration in QuakeML, not in SC3ML)
|
||||
* - Don't modify id if it starts with 'smi:' or 'quakeml:'
|
||||
* - Fix Arrival publicID generation
|
||||
*
|
||||
* * 27.09.2017:
|
||||
* - Use '_' instead of '#' in arrival publicID generation
|
||||
* - Map SC3 arrival weight to timeWeight, horizontalSlownessWeight and
|
||||
* backazimuthWeight depending on timeUsed, horizontalUsed and
|
||||
* backzimuthUsed values
|
||||
*
|
||||
* * 08.12.2017:
|
||||
* - Remove unmapped nodes
|
||||
* - Fix arrival weight mapping
|
||||
*
|
||||
* * 27.07.2018: Version bump. No modification here, SC3 datamodel was
|
||||
* extented by data availability top level element
|
||||
*
|
||||
* * 02.11.2018: Don't export stationMagnitude passedQC attribute
|
||||
*
|
||||
* * 01.11.2023:
|
||||
* - Skip originUncertaintyDescription if value is set to
|
||||
* 'probability density function' not supported by QuakeML.
|
||||
*
|
||||
* * 26.07.2024:
|
||||
* - Fix origin/confidenceEllipsoid conversion. The unit for
|
||||
* 'semiMajorAxisLength', 'semiMinorAxisLength' and
|
||||
* 'semiIntermediateAxisLength' is already meter and does not need a
|
||||
* conversion.
|
||||
*
|
||||
********************************************************************** -->
|
||||
<xsl:stylesheet version="1.0"
|
||||
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
|
||||
xmlns:scs="http://geofon.gfz-potsdam.de/ns/seiscomp3-schema/0.11"
|
||||
xmlns:qml="http://quakeml.org/xmlns/quakeml/1.0"
|
||||
xmlns="http://quakeml.org/xmlns/bed-rt/1.2"
|
||||
xmlns:q="http://quakeml.org/xmlns/quakeml-rt/1.2"
|
||||
exclude-result-prefixes="scs qml xsl">
|
||||
<xsl:output method="xml" encoding="UTF-8" indent="yes"/>
|
||||
<xsl:strip-space elements="*"/>
|
||||
|
||||
<!-- Define parameters-->
|
||||
<xsl:param name="ID_PREFIX" select="'smi:org.gfz-potsdam.de/geofon/'"/>
|
||||
|
||||
<!-- Define global variables -->
|
||||
<xsl:variable name="PID" select="'publicID'"/>
|
||||
|
||||
<!-- Starting point: Match the root node and select the one and only
|
||||
EventParameters node -->
|
||||
<xsl:template match="/">
|
||||
<xsl:variable name="scsRoot" select="."/>
|
||||
<q:quakeml>
|
||||
<xsl:for-each select="$scsRoot/scs:seiscomp/scs:EventParameters">
|
||||
<eventParameters>
|
||||
<!-- Mandatory publicID attribute -->
|
||||
<xsl:attribute name="{$PID}">
|
||||
<xsl:call-template name="convertOptionalID">
|
||||
<xsl:with-param name="id" select="@publicID"/>
|
||||
</xsl:call-template>
|
||||
</xsl:attribute>
|
||||
<!-- Move all origin/stationMagnitudes and origin/magitudes
|
||||
to this level -->
|
||||
<xsl:for-each select="scs:origin">
|
||||
<xsl:for-each select="scs:stationMagnitude">
|
||||
<xsl:apply-templates select="." mode="originMagnitude">
|
||||
<xsl:with-param name="oID" select="../@publicID"/>
|
||||
</xsl:apply-templates>
|
||||
</xsl:for-each>
|
||||
<xsl:for-each select="scs:magnitude">
|
||||
<xsl:apply-templates select="." mode="originMagnitude">
|
||||
<xsl:with-param name="oID" select="../@publicID"/>
|
||||
</xsl:apply-templates>
|
||||
</xsl:for-each>
|
||||
</xsl:for-each>
|
||||
|
||||
<xsl:apply-templates/>
|
||||
</eventParameters>
|
||||
</xsl:for-each>
|
||||
</q:quakeml>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Default match: Map node 1:1 -->
|
||||
<xsl:template match="*">
|
||||
<xsl:call-template name="genericNode"/>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Delete elements -->
|
||||
<xsl:template match="scs:creationInfo/scs:modificationTime"/>
|
||||
<xsl:template match="scs:comment/scs:id"/>
|
||||
<xsl:template match="scs:comment/scs:start"/>
|
||||
<xsl:template match="scs:comment/scs:end"/>
|
||||
<xsl:template match="scs:arrival/scs:weight"/>
|
||||
<xsl:template match="scs:arrival/scs:timeUsed"/>
|
||||
<xsl:template match="scs:arrival/scs:horizontalSlownessUsed"/>
|
||||
<xsl:template match="scs:arrival/scs:backazimuthUsed"/>
|
||||
<xsl:template match="scs:origin/scs:stationMagnitude"/>
|
||||
<xsl:template match="scs:origin/scs:magnitude"/>
|
||||
<xsl:template match="scs:momentTensor/scs:method"/>
|
||||
<xsl:template match="scs:momentTensor/scs:stationMomentTensorContribution"/>
|
||||
<xsl:template match="scs:momentTensor/scs:status"/>
|
||||
<xsl:template match="scs:momentTensor/scs:cmtName"/>
|
||||
<xsl:template match="scs:momentTensor/scs:cmtVersion"/>
|
||||
<xsl:template match="scs:momentTensor/scs:phaseSetting"/>
|
||||
<xsl:template match="scs:stationMagnitude/scs:passedQC"/>
|
||||
<xsl:template match="scs:pdf"/>
|
||||
|
||||
|
||||
<!-- event -->
|
||||
<xsl:template match="scs:event">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<xsl:apply-templates/>
|
||||
|
||||
<!-- Create network magnitude references referenced by origins of
|
||||
this event -->
|
||||
<xsl:for-each select="scs:originReference">
|
||||
<xsl:for-each select="../../scs:origin[@publicID=current()]/scs:magnitude/@publicID">
|
||||
<xsl:element name="magnitudeReference">
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="string(.)"/>
|
||||
</xsl:call-template>
|
||||
</xsl:element>
|
||||
</xsl:for-each>
|
||||
</xsl:for-each>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Converts a scs magnitude/stationMagnitude to a qml
|
||||
magnitude/stationMagnitude -->
|
||||
<xsl:template match="*" mode="originMagnitude">
|
||||
<xsl:param name="oID"/>
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<!-- if no originID element is available, create one with
|
||||
the value of the publicID attribute of parent origin -->
|
||||
<xsl:if test="not(scs:originID)">
|
||||
<originID>
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="$oID"/>
|
||||
</xsl:call-template>
|
||||
</originID>
|
||||
</xsl:if>
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- event type, enumeration differs slightly -->
|
||||
<xsl:template match="scs:event/scs:type">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:variable name="v" select="current()"/>
|
||||
<xsl:choose>
|
||||
<xsl:when test="$v='induced earthquake'">induced or triggered event</xsl:when>
|
||||
<xsl:when test="$v='meteor impact'">meteorite</xsl:when>
|
||||
<xsl:when test="$v='not locatable'">other event</xsl:when>
|
||||
<xsl:when test="$v='outside of network interest'">other event</xsl:when>
|
||||
<xsl:when test="$v='duplicate'">other event</xsl:when>
|
||||
<xsl:when test="$v='other'">other event</xsl:when>
|
||||
<xsl:otherwise><xsl:value-of select="$v"/></xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- origin depth, SC3ML uses kilometer, QML meter -->
|
||||
<xsl:template match="scs:origin/scs:depth/scs:value
|
||||
| scs:origin/scs:depth/scs:uncertainty
|
||||
| scs:origin/scs:depth/scs:lowerUncertainty
|
||||
| scs:origin/scs:depth/scs:upperUncertainty
|
||||
| scs:origin/scs:uncertainty/scs:horizontalUncertainty
|
||||
| scs:origin/scs:uncertainty/scs:minHorizontalUncertainty
|
||||
| scs:origin/scs:uncertainty/scs:maxHorizontalUncertainty">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:value-of select="current() * 1000"/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- evaluation status, enumeration of QML does not include 'reported' -->
|
||||
<xsl:template match="scs:evaluationStatus">
|
||||
<xsl:variable name="v" select="current()"/>
|
||||
<xsl:if test="$v!='reported'">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:value-of select="$v"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:template>
|
||||
|
||||
<!-- data used wave type, enumeration differs slightly -->
|
||||
<xsl:template match="scs:dataUsed/scs:waveType">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:variable name="v" select="current()"/>
|
||||
<xsl:choose>
|
||||
<xsl:when test="$v='P body waves'">P waves</xsl:when>
|
||||
<xsl:when test="$v='long-period body waves'">body waves</xsl:when>
|
||||
<xsl:when test="$v='intermediate-period surface waves'">surface waves</xsl:when>
|
||||
<xsl:when test="$v='long-period mantle waves'">mantle waves</xsl:when>
|
||||
<xsl:otherwise><xsl:value-of select="$v"/></xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- origin uncertainty description, enumeration of QML does not include 'probability density function' -->
|
||||
<xsl:template match="scs:origin/scs:uncertainty/scs:preferredDescription">
|
||||
<xsl:variable name="v" select="current()"/>
|
||||
<xsl:if test="$v!='probability density function'">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:value-of select="$v"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:template>
|
||||
|
||||
<!-- momentTensor/method -> momentTensor/category -->
|
||||
<xsl:template match="scs:momentTensor/scs:method">
|
||||
<xsl:variable name="v" select="current()"/>
|
||||
<xsl:if test="$v='teleseismic' or $v='regional'">
|
||||
<xsl:element name="category">
|
||||
<xsl:value-of select="$v"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:template>
|
||||
|
||||
<!-- amplitude/unit is an enumeration in QuakeML, not in SC3ML -->
|
||||
<xsl:template match="scs:amplitude/scs:unit">
|
||||
<xsl:variable name="v" select="current()"/>
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:choose>
|
||||
<xsl:when test="$v='m'
|
||||
or $v='s'
|
||||
or $v='m/s'
|
||||
or $v='m/(s*s)'
|
||||
or $v='m*s'
|
||||
or $v='dimensionless'">
|
||||
<xsl:value-of select="$v"/>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>other</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- origin arrival -->
|
||||
<xsl:template match="scs:arrival">
|
||||
<xsl:element name="{local-name()}">
|
||||
<!-- since SC3ML does not include a publicID it is generated from pick and origin id -->
|
||||
<xsl:attribute name="{$PID}">
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="concat(scs:pickID, '_', translate(../@publicID, ' :', '__'))"/>
|
||||
</xsl:call-template>
|
||||
</xsl:attribute>
|
||||
<!-- mapping of weight to timeWeight, horizontalSlownessWeight and backazimuthWeight
|
||||
depending on timeUsed, horizontalSlownessUsed and backazimuthUsed values -->
|
||||
<xsl:choose>
|
||||
<xsl:when test="scs:weight">
|
||||
<xsl:if test="((scs:timeUsed='true') or (scs:timeUsed='1'))
|
||||
or (not(scs:timeUsed|scs:horizontalSlownessUsed|scs:backazimuthUsed))">
|
||||
<xsl:element name="timeWeight">
|
||||
<xsl:value-of select="scs:weight"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
<xsl:if test="((scs:horizontalSlownessUsed='true') or (scs:horizontalSlownessUsed='1'))">
|
||||
<xsl:element name="horizontalSlownessWeight">
|
||||
<xsl:value-of select="scs:weight"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
<xsl:if test="((scs:backazimuthUsed='true') or (scs:backazimuthUsed='1'))">
|
||||
<xsl:element name="backazimuthWeight">
|
||||
<xsl:value-of select="scs:weight"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>
|
||||
<xsl:if test="((scs:timeUsed='true') or (scs:timeUsed='1'))">
|
||||
<xsl:element name="timeWeight">
|
||||
<xsl:value-of select="'1'"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
<xsl:if test="((scs:horizontalSlownessUsed='true') or (scs:horizontalSlownessUsed='1'))">
|
||||
<xsl:element name="horizontalSlownessWeight">
|
||||
<xsl:value-of select="'1'"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
<xsl:if test="((scs:backazimuthUsed='true') or (scs:backazimuthUsed='1'))">
|
||||
<xsl:element name="backazimuthWeight">
|
||||
<xsl:value-of select="'1'"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Value of ID nodes must be converted to a qml identifier -->
|
||||
<xsl:template match="scs:agencyURI|scs:authorURI|scs:pickID|scs:methodID|scs:earthModelID|scs:amplitudeID|scs:originID|scs:stationMagnitudeID|scs:preferredOriginID|scs:preferredMagnitudeID|scs:originReference|scs:filterID|scs:slownessMethodID|scs:pickReference|scs:amplitudeReference|scs:referenceSystemID|scs:triggeringOriginID|scs:derivedOriginID|momentMagnitudeID|scs:preferredFocalMechanismID|scs:focalMechanismReference|scs:momentMagnitudeID|scs:greensFunctionID">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<xsl:call-template name="valueOfIDNode"/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- arrival/takeOffAngle -> arrival/takeoffAngle -->
|
||||
<xsl:template match="scs:arrival/scs:takeOffAngle">
|
||||
<xsl:element name="takeoffAngle">
|
||||
<xsl:element name="value">
|
||||
<xsl:value-of select="."/>
|
||||
</xsl:element>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- stationMagnitude/magnitude -> stationMagnitude/mag -->
|
||||
<xsl:template match="scs:stationMagnitude/scs:magnitude|scs:magnitude/scs:magnitude">
|
||||
<xsl:call-template name="genericNode">
|
||||
<xsl:with-param name="name" select="'mag'"/>
|
||||
</xsl:call-template>
|
||||
</xsl:template>
|
||||
|
||||
<!-- amplitude/amplitude -> amplitude/genericAmplitude -->
|
||||
<xsl:template match="scs:amplitude/scs:amplitude">
|
||||
<xsl:call-template name="genericNode">
|
||||
<xsl:with-param name="name" select="'genericAmplitude'"/>
|
||||
</xsl:call-template>
|
||||
</xsl:template>
|
||||
|
||||
<!-- origin/uncertainty -> origin/originUncertainty -->
|
||||
<xsl:template match="scs:origin/scs:uncertainty">
|
||||
<xsl:call-template name="genericNode">
|
||||
<xsl:with-param name="name" select="'originUncertainty'"/>
|
||||
</xsl:call-template>
|
||||
</xsl:template>
|
||||
|
||||
<!-- originUncertaintyDescription, enumeration of QML does not
|
||||
include 'probability density function' -->
|
||||
<xsl:template match="scs:originUncertaintyDescription">
|
||||
<xsl:variable name="v" select="current()"/>
|
||||
<xsl:if test="$v!='probability density function'">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:value-of select="$v"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:template>
|
||||
|
||||
<!-- waveformID: SCS uses a child element 'resourceURI', QML
|
||||
inserts the URI directly as value -->
|
||||
<xsl:template match="scs:waveformID">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<xsl:if test="scs:resourceURI">
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="scs:resourceURI"/>
|
||||
</xsl:call-template>
|
||||
</xsl:if>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- comment: SCS uses a child element 'id', QML an attribute 'id' -->
|
||||
<xsl:template match="scs:comment">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:if test="scs:id">
|
||||
<xsl:attribute name="id">
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="scs:id"/>
|
||||
</xsl:call-template>
|
||||
</xsl:attribute>
|
||||
</xsl:if>
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Generic transformation of all attributes of an element. If the
|
||||
attribute name is 'eventID' it is transfered to a QML id -->
|
||||
<xsl:template match="@*">
|
||||
<xsl:variable name="attName" select="local-name()"/>
|
||||
<xsl:attribute name="{$attName}">
|
||||
<xsl:choose>
|
||||
<xsl:when test="$attName=$PID">
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="string(.)"/>
|
||||
</xsl:call-template>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>
|
||||
<xsl:value-of select="string(.)"/>
|
||||
</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:attribute>
|
||||
</xsl:template>
|
||||
|
||||
<!--
|
||||
************************************************************************
|
||||
Named Templates
|
||||
************************************************************************
|
||||
-->
|
||||
|
||||
<!-- Generic and recursively transformation of elements and their
|
||||
attributes -->
|
||||
<xsl:template name="genericNode">
|
||||
<xsl:param name="name"/>
|
||||
<xsl:param name="reqPID"/>
|
||||
<xsl:variable name="nodeName">
|
||||
<xsl:choose>
|
||||
<xsl:when test="$name">
|
||||
<xsl:value-of select="$name"/>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>
|
||||
<xsl:value-of select="local-name()"/>
|
||||
</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:variable>
|
||||
<xsl:element name="{$nodeName}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<xsl:if test="$reqPID">
|
||||
<xsl:attribute name="{$PID}">
|
||||
<xsl:call-template name="convertOptionalID">
|
||||
<xsl:with-param name="id" select="@publicID"/>
|
||||
</xsl:call-template>
|
||||
</xsl:attribute>
|
||||
</xsl:if>
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Converts and returns value of an id node -->
|
||||
<xsl:template name="valueOfIDNode">
|
||||
<xsl:call-template name="convertOptionalID">
|
||||
<xsl:with-param name="id" select="string(.)"/>
|
||||
</xsl:call-template>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Converts a scs id to a quakeml id. If the scs id is not set
|
||||
the constant 'NA' is used -->
|
||||
<xsl:template name="convertOptionalID">
|
||||
<xsl:param name="id"/>
|
||||
<xsl:choose>
|
||||
<xsl:when test="$id">
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="$id"/>
|
||||
</xsl:call-template>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>
|
||||
<xsl:call-template name="convertID">
|
||||
<!--xsl:with-param name="id" select="concat('NA-', generate-id())"/-->
|
||||
<xsl:with-param name="id" select="'NA'"/>
|
||||
</xsl:call-template>
|
||||
</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Converts a scs id to a quakeml id -->
|
||||
<xsl:template name="convertID">
|
||||
<xsl:param name="id"/>
|
||||
<!-- If the id starts with 'smi:' or 'quakeml:', consider that the id
|
||||
is already well formated -->
|
||||
<xsl:choose>
|
||||
<xsl:when test="starts-with($id, 'smi:')
|
||||
or starts-with($id, 'quakeml:')">
|
||||
<xsl:value-of select="$id"/>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>
|
||||
<xsl:value-of select="concat($ID_PREFIX, translate($id, ' :', '__'))"/>
|
||||
</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:template>
|
||||
|
||||
</xsl:stylesheet>
|
702
share/xml/0.11/sc3ml_0.11__quakeml_1.2.xsl
Normal file
702
share/xml/0.11/sc3ml_0.11__quakeml_1.2.xsl
Normal file
@ -0,0 +1,702 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!-- **********************************************************************
|
||||
* Copyright (C) 2017 by gempa GmbH
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Lesser General Public License as
|
||||
* published by the Free Software Foundation, version 3.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful, but
|
||||
* WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
* Lesser General Lesser Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*
|
||||
* SC3ML 0.11 to QuakeML 1.2 stylesheet converter
|
||||
* Author : Stephan Herrnkind
|
||||
* Email : stephan.herrnkind@gempa.de
|
||||
* Version : 2017.342.01
|
||||
*
|
||||
* ================
|
||||
* Usage
|
||||
* ================
|
||||
*
|
||||
* This stylesheet converts a SC3ML to a QuakeML document. It may be invoked
|
||||
* e.g. using xalan or xsltproc:
|
||||
*
|
||||
* xalan -in sc3ml.xml -xsl sc3ml_0.11__quakeml_1.2.xsl -out quakeml.xml
|
||||
* xsltproc -o quakeml.xml sc3ml_0.11__quakeml_1.2.xsl sc3ml.xml
|
||||
*
|
||||
* You can also modify the default ID prefix with the reverse DNS name of your
|
||||
* institute by setting the ID_PREFIX param:
|
||||
*
|
||||
* xalan -param ID_PREFIX "'smi:org.gfz-potsdam.de/geofon/'" -in sc3ml.xml -xsl sc3ml_0.11__quakeml_1.2.xsl -out quakeml.xml
|
||||
* xsltproc -stringparam ID_PREFIX smi:org.gfz-potsdam.de/geofon/ -o quakeml.xml sc3ml_0.11__quakeml_1.2.xsl sc3ml.xml
|
||||
*
|
||||
* ================
|
||||
* Transformation
|
||||
* ================
|
||||
*
|
||||
* QuakeML and SC3ML are quite similar schemas. Nevertheless some differences
|
||||
* exist:
|
||||
*
|
||||
* - IDs : SC3ML does not enforce any particular ID restriction. An ID in
|
||||
* SC3ML has no semantic, it simply must be unique. Hence QuakeML uses ID
|
||||
* restrictions, a conversion of a SC3ML to a QuakeML ID must be performed:
|
||||
* 'sc3id' -> 'smi:org.gfz-potsdam.de/geofon/'. If no SC3ML ID is available
|
||||
* but QuakeML enforces one, a static ID value of 'NA' is used.
|
||||
* If the ID starts with `smi:` or `quakeml:`, the ID is considered valid
|
||||
* and let untouched. This can lead to an invalid generated file but avoid
|
||||
* to always modify IDs, especially when converting several times.
|
||||
* - Repositioning of nodes: In QuakeML all information is grouped under the
|
||||
* event element. As a consequence every node not referenced by an event
|
||||
* will be lost during the conversion.
|
||||
*
|
||||
* <EventParameters> <eventParameters>
|
||||
* <event>
|
||||
* <pick/> <pick/>
|
||||
* <amplitude/> <amplitude/>
|
||||
* <reading/>
|
||||
* <origin> <origin/>
|
||||
* <stationMagnitude/> <stationMagnitude/>
|
||||
* <magnitude/> <magnitude/>
|
||||
* </origin>
|
||||
* <focalMechanism/> <focalMechanism/>
|
||||
* <event/> </event>
|
||||
* </EventParameters> </eventParameters>
|
||||
*
|
||||
* - Renaming of nodes: The following table lists the mapping of names between
|
||||
* both schema:
|
||||
*
|
||||
* Parent (SC3) SC3 name QuakeML name
|
||||
* """""""""""""""""""""""""""""""""""""""""""""""""""""""
|
||||
* seiscomp EventParameters eventParameters
|
||||
* arrival weight [copied to following fields if true]
|
||||
* timeUsed timeWeight
|
||||
* horizontalSlownessUsed horizontalSlownessWeight
|
||||
* backazimuthUsed backazimuthWeight
|
||||
* takeOffAngle takeoffAngle
|
||||
* magnitude magnitude mag
|
||||
* stationMagnitude magnitude mag
|
||||
* amplitude amplitude genericAmplitude
|
||||
* origin uncertainty originUncertainty
|
||||
* momentTensor method category
|
||||
* waveformID resourceURI CDATA
|
||||
* comment id id (attribute)
|
||||
*
|
||||
* - Enumerations: Both schema use enumerations. Numerous mappings are applied.
|
||||
*
|
||||
* - Unit conversion: SC3ML uses kilometer for origin depth and origin
|
||||
* uncertainty, QuakeML uses meter
|
||||
*
|
||||
* - Unmapped nodes: The following nodes can not be mapped to the QuakeML
|
||||
* schema, thus their data is lost:
|
||||
*
|
||||
* Parent Element lost
|
||||
* """""""""""""""""""""""""""""""""""""""""""""""""""""""""""
|
||||
* creationInfo modificationTime
|
||||
* momentTensor method
|
||||
* stationMomentTensorContribution
|
||||
* status
|
||||
* cmtName
|
||||
* cmtVersion
|
||||
* phaseSetting
|
||||
* stationMagnitude passedQC
|
||||
* eventParameters reading
|
||||
* comment start
|
||||
* comment end
|
||||
* RealQuantity pdf
|
||||
* TimeQuality pdf
|
||||
*
|
||||
* - Mandatory nodes: The following nodes is mandatory in QuakeML but not in
|
||||
* SC3ML:
|
||||
*
|
||||
* Parent Mandatory element
|
||||
* """"""""""""""""""""""""""""""""""""""""""""""""""""""""""
|
||||
* Amplitude genericAmplitude
|
||||
* StationMagnitude originID
|
||||
*
|
||||
* - Restriction of data size: QuakeML restricts string length of some
|
||||
* elements. This length restriction is _NOT_ enforced by this
|
||||
* stylesheet to prevent data loss. As a consequence QuakeML files
|
||||
* generated by this XSLT may not validate because of these
|
||||
* restrictions.
|
||||
*
|
||||
* ================
|
||||
* Change log
|
||||
* ================
|
||||
*
|
||||
* * 08.09.2014: Fixed typo in event type conversion (meteo[r] impact)
|
||||
*
|
||||
* * 25.08.2014: Applied part of the patch proposed by Philipp Kaestli on
|
||||
* seiscomp-l@gfz-potsdam.de
|
||||
* - use public id of parent origin if origin id propertery of magnitude
|
||||
* and station magnitude elements is unset
|
||||
* - fixed takeOffAngle conversion vom real (SC3ML) to RealQuantity
|
||||
* (QuakeML)
|
||||
*
|
||||
* * 04.07.2016: Version bump. No modification here, SC3 datamodel was updated
|
||||
* on the inventory side.
|
||||
*
|
||||
* * 28.11.2016: Version bump. No modification here, SC3 datamodel was updated
|
||||
* on the inventory side.
|
||||
*
|
||||
* * 28.06.2017: Changed license from GPL to LGPL
|
||||
*
|
||||
* * 08.08.2017: Added some fixes to use this XSLT in ObsPy
|
||||
* - Change ID_PREFIX variable to a param
|
||||
* - Do not copy Amplitude if amplitude/amplitude doesn't existing
|
||||
* - focalMechanism/evaluationMode and focalMechanism/evaluationStatus were
|
||||
* not copied but can actually be mapped to the QuakeML schema
|
||||
* - Some event/type enumeration was mapped to `other` instead of
|
||||
* `other event`
|
||||
* - Fix origin uncertainty and confidence ellispoid units
|
||||
* - Rename momentTensor/method to momentTensor/category
|
||||
* - Fix amplitude/unit (enumeration in QuakeML, not in SC3ML)
|
||||
* - Don't modify id if it starts with 'smi:' or 'quakeml:'
|
||||
* - Fix Arrival publicID generation
|
||||
*
|
||||
* * 27.09.2017:
|
||||
* - Use '_' instead of '#' in arrival publicID generation
|
||||
* - Map SC3 arrival weight to timeWeight, horizontalSlownessWeight and
|
||||
* backazimuthWeight depending on timeUsed, horizontalUsed and
|
||||
* backzimuthUsed values
|
||||
*
|
||||
* * 08.12.2017:
|
||||
* - Remove unmapped nodes
|
||||
* - Fix arrival weight mapping
|
||||
*
|
||||
* * 27.07.2018: Version bump. No modification here, SC3 datamodel was
|
||||
* extented by data availability top level element
|
||||
*
|
||||
* * 02.11.2018: Don't export stationMagnitude passedQC attribute
|
||||
*
|
||||
* * 07.12.2018: Copy picks referenced by amplitudes
|
||||
*
|
||||
* * 10.12.2018: Put the non-QuakeML nodes in a custom namespace
|
||||
*
|
||||
* * 04.04.2022:
|
||||
* - Skip originUncertaintyDescription if value is set to
|
||||
* 'probability density function' not supported by QuakeML.
|
||||
*
|
||||
* * 31.10.2022: Improve performance when processing origins with many arrivals.
|
||||
*
|
||||
* * 24.03.2023:
|
||||
* - Do not export duplicated picks referenced by different amplitudes.
|
||||
*
|
||||
* * 26.07.2024:
|
||||
* - Fix origin/confidenceEllipsoid conversion. The unit for
|
||||
* 'semiMajorAxisLength', 'semiMinorAxisLength' and
|
||||
* 'semiIntermediateAxisLength' is already meter and does not need a
|
||||
* conversion.
|
||||
*
|
||||
********************************************************************** -->
|
||||
<xsl:stylesheet version="1.0"
|
||||
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
|
||||
xmlns:scs="http://geofon.gfz-potsdam.de/ns/seiscomp3-schema/0.11"
|
||||
xmlns:qml="http://quakeml.org/xmlns/quakeml/1.0"
|
||||
xmlns="http://quakeml.org/xmlns/bed/1.2"
|
||||
xmlns:q="http://quakeml.org/xmlns/quakeml/1.2"
|
||||
exclude-result-prefixes="scs qml xsl">
|
||||
<xsl:output method="xml" encoding="UTF-8" indent="yes"/>
|
||||
<xsl:strip-space elements="*"/>
|
||||
|
||||
<!-- Define parameters-->
|
||||
<xsl:param name="ID_PREFIX" select="'smi:org.gfz-potsdam.de/geofon/'"/>
|
||||
|
||||
<!-- Define global variables -->
|
||||
<xsl:variable name="PID" select="'publicID'"/>
|
||||
|
||||
<!-- Starting point: Match the root node and select the one and only
|
||||
EventParameters node -->
|
||||
<xsl:template match="/">
|
||||
<xsl:variable name="scsRoot" select="."/>
|
||||
<q:quakeml>
|
||||
<xsl:for-each select="$scsRoot/scs:seiscomp/scs:EventParameters">
|
||||
<eventParameters>
|
||||
<!-- Mandatory publicID attribute -->
|
||||
<xsl:attribute name="{$PID}">
|
||||
<xsl:call-template name="convertOptionalID">
|
||||
<xsl:with-param name="id" select="@publicID"/>
|
||||
</xsl:call-template>
|
||||
</xsl:attribute>
|
||||
|
||||
<!-- Put the QuakeML nodes at the beginning -->
|
||||
<xsl:apply-templates select="*[not(self::scs:reading)]" />
|
||||
<!-- Put the non-QuakeML nodes at the end -->
|
||||
<xsl:apply-templates select="scs:reading" mode="scs-only" />
|
||||
</eventParameters>
|
||||
</xsl:for-each>
|
||||
</q:quakeml>
|
||||
</xsl:template>
|
||||
|
||||
<!-- event -->
|
||||
<xsl:template match="scs:event">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
|
||||
<!-- collect origins referenced by event/originReference -->
|
||||
<xsl:variable name="origins" select="../scs:origin[@publicID=current()/scs:originReference]" />
|
||||
|
||||
<!-- picks referenced via origin/stationMagnitude/amplitudeID or origin/arrival -->
|
||||
<xsl:variable name="amplitudes" select="../scs:amplitude[@publicID=$origins/scs:stationMagnitude/scs:amplitudeID]" />
|
||||
<xsl:variable name="picks" select="$origins/scs:arrival/scs:pickID | $amplitudes/scs:pickID" />
|
||||
<xsl:for-each select="../scs:pick[@publicID = $picks]">
|
||||
<xsl:call-template name="genericNode" />
|
||||
</xsl:for-each>
|
||||
|
||||
<xsl:for-each select="$origins">
|
||||
|
||||
<!-- stationMagnitudes and referenced amplitudes -->
|
||||
<xsl:for-each select="scs:stationMagnitude">
|
||||
<xsl:for-each select="../../scs:amplitude[@publicID=current()/scs:amplitudeID]">
|
||||
<!-- amplitude/genericAmplitude is mandatory in QuakeML -->
|
||||
<xsl:if test="scs:amplitude">
|
||||
<xsl:call-template name="genericNode"/>
|
||||
</xsl:if>
|
||||
</xsl:for-each>
|
||||
<xsl:apply-templates select="." mode="originMagnitude">
|
||||
<xsl:with-param name="oID" select="../@publicID"/>
|
||||
</xsl:apply-templates>
|
||||
</xsl:for-each>
|
||||
|
||||
<!-- magnitudes -->
|
||||
<xsl:for-each select="scs:magnitude">
|
||||
<xsl:apply-templates select="." mode="originMagnitude">
|
||||
<xsl:with-param name="oID" select="../@publicID"/>
|
||||
</xsl:apply-templates>
|
||||
</xsl:for-each>
|
||||
|
||||
<!-- origin -->
|
||||
<xsl:call-template name="genericNode"/>
|
||||
</xsl:for-each>
|
||||
|
||||
<!-- search focalMechanisms referenced by this event -->
|
||||
<xsl:for-each select="scs:focalMechanismReference">
|
||||
<xsl:for-each select="../../scs:focalMechanism[@publicID=current()]">
|
||||
<xsl:call-template name="genericNode"/>
|
||||
</xsl:for-each>
|
||||
</xsl:for-each>
|
||||
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Default match: Map node 1:1 -->
|
||||
<xsl:template match="*">
|
||||
<xsl:call-template name="genericNode"/>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Delete elements -->
|
||||
<xsl:template match="scs:EventParameters/scs:pick"/>
|
||||
<xsl:template match="scs:EventParameters/scs:amplitude"/>
|
||||
<xsl:template match="scs:EventParameters/scs:origin"/>
|
||||
<xsl:template match="scs:EventParameters/scs:focalMechanism"/>
|
||||
<xsl:template match="scs:event/scs:originReference"/>
|
||||
<xsl:template match="scs:event/scs:focalMechanismReference"/>
|
||||
<xsl:template match="scs:comment/scs:id"/>
|
||||
<xsl:template match="scs:arrival/scs:weight"/>
|
||||
<xsl:template match="scs:arrival/scs:timeUsed"/>
|
||||
<xsl:template match="scs:arrival/scs:horizontalSlownessUsed"/>
|
||||
<xsl:template match="scs:arrival/scs:backazimuthUsed"/>
|
||||
<xsl:template match="scs:origin/scs:stationMagnitude"/>
|
||||
<xsl:template match="scs:origin/scs:magnitude"/>
|
||||
<xsl:template match="scs:momentTensor/scs:method"/>
|
||||
|
||||
<!-- Converts a scs magnitude/stationMagnitude to a qml
|
||||
magnitude/stationMagnitude -->
|
||||
<xsl:template match="*" mode="originMagnitude">
|
||||
<xsl:param name="oID"/>
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<!-- if no originID element is available, create one with
|
||||
the value of the publicID attribute of parent origin -->
|
||||
<xsl:if test="not(scs:originID)">
|
||||
<originID>
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="$oID"/>
|
||||
</xsl:call-template>
|
||||
</originID>
|
||||
</xsl:if>
|
||||
|
||||
<!-- Put the QuakeML nodes at the beginning -->
|
||||
<xsl:apply-templates select="*[not(self::scs:passedQC)]" />
|
||||
<!-- Put the non-QuakeML nodes at the end -->
|
||||
<xsl:apply-templates select="scs:passedQC" mode="scs-only" />
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- event type, enumeration differs slightly -->
|
||||
<xsl:template match="scs:event/scs:type">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:variable name="v" select="current()"/>
|
||||
<xsl:choose>
|
||||
<xsl:when test="$v='induced earthquake'">induced or triggered event</xsl:when>
|
||||
<xsl:when test="$v='meteor impact'">meteorite</xsl:when>
|
||||
<xsl:when test="$v='not locatable'">other event</xsl:when>
|
||||
<xsl:when test="$v='outside of network interest'">other event</xsl:when>
|
||||
<xsl:when test="$v='duplicate'">other event</xsl:when>
|
||||
<xsl:when test="$v='other'">other event</xsl:when>
|
||||
<xsl:otherwise><xsl:value-of select="$v"/></xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- origin depth, SC3ML uses kilometer, QML meter -->
|
||||
<xsl:template match="scs:origin/scs:depth/scs:value
|
||||
| scs:origin/scs:depth/scs:uncertainty
|
||||
| scs:origin/scs:depth/scs:lowerUncertainty
|
||||
| scs:origin/scs:depth/scs:upperUncertainty
|
||||
| scs:origin/scs:uncertainty/scs:horizontalUncertainty
|
||||
| scs:origin/scs:uncertainty/scs:minHorizontalUncertainty
|
||||
| scs:origin/scs:uncertainty/scs:maxHorizontalUncertainty">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:value-of select="current() * 1000"/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- evaluation status, enumeration of QML does not include 'reported' -->
|
||||
<xsl:template match="scs:evaluationStatus">
|
||||
<xsl:variable name="v" select="current()"/>
|
||||
<xsl:if test="$v!='reported'">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:value-of select="$v"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:template>
|
||||
|
||||
<!-- data used wave type, enumeration differs slightly -->
|
||||
<xsl:template match="scs:dataUsed/scs:waveType">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:variable name="v" select="current()"/>
|
||||
<xsl:choose>
|
||||
<xsl:when test="$v='P body waves'">P waves</xsl:when>
|
||||
<xsl:when test="$v='long-period body waves'">body waves</xsl:when>
|
||||
<xsl:when test="$v='intermediate-period surface waves'">surface waves</xsl:when>
|
||||
<xsl:when test="$v='long-period mantle waves'">mantle waves</xsl:when>
|
||||
<xsl:otherwise><xsl:value-of select="$v"/></xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- origin uncertainty description, enumeration of QML does not include 'probability density function' -->
|
||||
<xsl:template match="scs:origin/scs:uncertainty/scs:preferredDescription">
|
||||
<xsl:variable name="v" select="current()"/>
|
||||
<xsl:if test="$v!='probability density function'">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:value-of select="$v"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:template>
|
||||
|
||||
<!-- origin uncertainty description, enumeration of QML does not include 'probability density function' -->
|
||||
<xsl:template match="scs:origin/scs:uncertainty/scs:preferredDescription">
|
||||
<xsl:variable name="v" select="current()"/>
|
||||
<xsl:if test="$v!='probability density function'">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:value-of select="$v"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:template>
|
||||
|
||||
<!-- momentTensor/method -> momentTensor/category -->
|
||||
<xsl:template match="scs:momentTensor/scs:method">
|
||||
<xsl:variable name="v" select="current()"/>
|
||||
<xsl:if test="$v='teleseismic' or $v='regional'">
|
||||
<xsl:element name="category">
|
||||
<xsl:value-of select="$v"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:template>
|
||||
|
||||
<!-- amplitude/unit is an enumeration in QuakeML, not in SC3ML -->
|
||||
<xsl:template match="scs:amplitude/scs:unit">
|
||||
<xsl:variable name="v" select="current()"/>
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:choose>
|
||||
<xsl:when test="$v='m'
|
||||
or $v='s'
|
||||
or $v='m/s'
|
||||
or $v='m/(s*s)'
|
||||
or $v='m*s'
|
||||
or $v='dimensionless'">
|
||||
<xsl:value-of select="$v"/>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>other</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- origin arrival -->
|
||||
<xsl:template match="scs:arrival">
|
||||
<xsl:element name="{local-name()}">
|
||||
<!-- since SC3ML does not include a publicID it is generated from pick and origin id -->
|
||||
<xsl:attribute name="{$PID}">
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="concat(scs:pickID, '_', translate(../@publicID, ' :', '__'))"/>
|
||||
</xsl:call-template>
|
||||
</xsl:attribute>
|
||||
<!-- mapping of weight to timeWeight, horizontalSlownessWeight and backazimuthWeight
|
||||
depending on timeUsed, horizontalSlownessUsed and backazimuthUsed values -->
|
||||
<xsl:choose>
|
||||
<xsl:when test="scs:weight">
|
||||
<xsl:if test="((scs:timeUsed='true') or (scs:timeUsed='1'))
|
||||
or (not(scs:timeUsed|scs:horizontalSlownessUsed|scs:backazimuthUsed))">
|
||||
<xsl:element name="timeWeight">
|
||||
<xsl:value-of select="scs:weight"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
<xsl:if test="((scs:horizontalSlownessUsed='true') or (scs:horizontalSlownessUsed='1'))">
|
||||
<xsl:element name="horizontalSlownessWeight">
|
||||
<xsl:value-of select="scs:weight"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
<xsl:if test="((scs:backazimuthUsed='true') or (scs:backazimuthUsed='1'))">
|
||||
<xsl:element name="backazimuthWeight">
|
||||
<xsl:value-of select="scs:weight"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>
|
||||
<xsl:if test="((scs:timeUsed='true') or (scs:timeUsed='1'))">
|
||||
<xsl:element name="timeWeight">
|
||||
<xsl:value-of select="'1'"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
<xsl:if test="((scs:horizontalSlownessUsed='true') or (scs:horizontalSlownessUsed='1'))">
|
||||
<xsl:element name="horizontalSlownessWeight">
|
||||
<xsl:value-of select="'1'"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
<xsl:if test="((scs:backazimuthUsed='true') or (scs:backazimuthUsed='1'))">
|
||||
<xsl:element name="backazimuthWeight">
|
||||
<xsl:value-of select="'1'"/>
|
||||
</xsl:element>
|
||||
</xsl:if>
|
||||
</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Value of ID nodes must be converted to a qml identifier -->
|
||||
<xsl:template match="scs:agencyURI|scs:authorURI|scs:pickID|scs:methodID|scs:earthModelID|scs:amplitudeID|scs:originID|scs:stationMagnitudeID|scs:preferredOriginID|scs:preferredMagnitudeID|scs:originReference|scs:filterID|scs:slownessMethodID|scs:pickReference|scs:amplitudeReference|scs:referenceSystemID|scs:triggeringOriginID|scs:derivedOriginID|momentMagnitudeID|scs:preferredFocalMechanismID|scs:focalMechanismReference|scs:momentMagnitudeID|scs:greensFunctionID">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<xsl:call-template name="valueOfIDNode"/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- arrival/takeOffAngle -> arrival/takeoffAngle -->
|
||||
<xsl:template match="scs:arrival/scs:takeOffAngle">
|
||||
<xsl:element name="takeoffAngle">
|
||||
<xsl:element name="value">
|
||||
<xsl:value-of select="."/>
|
||||
</xsl:element>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- stationMagnitude/magnitude -> stationMagnitude/mag -->
|
||||
<xsl:template match="scs:stationMagnitude/scs:magnitude|scs:magnitude/scs:magnitude">
|
||||
<xsl:call-template name="genericNode">
|
||||
<xsl:with-param name="name" select="'mag'"/>
|
||||
</xsl:call-template>
|
||||
</xsl:template>
|
||||
|
||||
<!-- amplitude/amplitude -> amplitude/genericAmplitude -->
|
||||
<xsl:template match="scs:amplitude/scs:amplitude">
|
||||
<xsl:call-template name="genericNode">
|
||||
<xsl:with-param name="name" select="'genericAmplitude'"/>
|
||||
</xsl:call-template>
|
||||
</xsl:template>
|
||||
|
||||
<!-- origin/uncertainty -> origin/originUncertainty -->
|
||||
<xsl:template match="scs:origin/scs:uncertainty">
|
||||
<xsl:call-template name="genericNode">
|
||||
<xsl:with-param name="name" select="'originUncertainty'"/>
|
||||
</xsl:call-template>
|
||||
</xsl:template>
|
||||
|
||||
<!-- waveformID: SCS uses a child element 'resourceURI', QML
|
||||
inserts the URI directly as value -->
|
||||
<xsl:template match="scs:waveformID">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<xsl:if test="scs:resourceURI">
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="scs:resourceURI"/>
|
||||
</xsl:call-template>
|
||||
</xsl:if>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- comment: SCS uses a child element 'id', QML an attribute 'id' -->
|
||||
<xsl:template match="scs:comment">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:if test="scs:id">
|
||||
<xsl:attribute name="id">
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="scs:id"/>
|
||||
</xsl:call-template>
|
||||
</xsl:attribute>
|
||||
</xsl:if>
|
||||
|
||||
<!-- Put the QuakeML nodes at the beginning -->
|
||||
<xsl:apply-templates select="*[not(self::scs:start|self::scs:end)]" />
|
||||
<!-- Put the non-QuakeML nodes at the end -->
|
||||
<xsl:apply-templates select="scs:start|scs:end" mode="scs-only" />
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Generic transformation of all attributes of an element. If the
|
||||
attribute name is 'eventID' it is transfered to a QML id -->
|
||||
<xsl:template match="@*">
|
||||
<xsl:variable name="attName" select="local-name()"/>
|
||||
<xsl:attribute name="{$attName}">
|
||||
<xsl:choose>
|
||||
<xsl:when test="$attName=$PID">
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="string(.)"/>
|
||||
</xsl:call-template>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>
|
||||
<xsl:value-of select="string(.)"/>
|
||||
</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:attribute>
|
||||
</xsl:template>
|
||||
|
||||
<!--
|
||||
************************************************************************
|
||||
Unmapped nodes
|
||||
************************************************************************
|
||||
-->
|
||||
|
||||
<xsl:template match="scs:creationInfo">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
|
||||
<!-- Put the QuakeML nodes at the beginning -->
|
||||
<xsl:apply-templates select="*[not(self::scs:modificationTime)]" />
|
||||
<!-- Put the non-QuakeML nodes at the end -->
|
||||
<xsl:apply-templates select="scs:modificationTime" mode="scs-only" />
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<xsl:template match="scs:momentTensor">
|
||||
<xsl:element name="{local-name()}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
|
||||
<!-- Put the QuakeML nodes at the beginning -->
|
||||
<xsl:apply-templates select="*[not(self::scs:stationMomentTensorContribution
|
||||
| self::scs:status
|
||||
| self::scs:cmtName
|
||||
| self::scs:cmtVersion
|
||||
| self::scs:phaseSetting)]" />
|
||||
<!-- Put the non-QuakeML nodes at the end -->
|
||||
<xsl:apply-templates select="scs:stationMomentTensorContribution
|
||||
| scs:status
|
||||
| scs:cmtName
|
||||
| scs:cmtVersion
|
||||
| scs:phaseSetting" mode="scs-only" />
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<xsl:template match="scs:pdf">
|
||||
<xsl:apply-templates select="." mode="scs-only" />
|
||||
</xsl:template>
|
||||
|
||||
<xsl:template match="node()|@*" mode="scs-only">
|
||||
<xsl:copy>
|
||||
<xsl:apply-templates select="node()|@*"/>
|
||||
</xsl:copy>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Keep seiscomp namespace for unmapped node -->
|
||||
<xsl:template match="scs:*" mode="scs-only">
|
||||
<xsl:element name="scs:{local-name()}">
|
||||
<xsl:apply-templates select="@*|node()" mode="scs-only" />
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
|
||||
<!--
|
||||
************************************************************************
|
||||
Named Templates
|
||||
************************************************************************
|
||||
-->
|
||||
|
||||
<!-- Generic and recursively transformation of elements and their
|
||||
attributes -->
|
||||
<xsl:template name="genericNode">
|
||||
<xsl:param name="name"/>
|
||||
<xsl:param name="reqPID"/>
|
||||
<xsl:variable name="nodeName">
|
||||
<xsl:choose>
|
||||
<xsl:when test="$name">
|
||||
<xsl:value-of select="$name"/>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>
|
||||
<xsl:value-of select="local-name()"/>
|
||||
</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:variable>
|
||||
<xsl:element name="{$nodeName}">
|
||||
<xsl:apply-templates select="@*"/>
|
||||
<xsl:if test="$reqPID">
|
||||
<xsl:attribute name="{$PID}">
|
||||
<xsl:call-template name="convertOptionalID">
|
||||
<xsl:with-param name="id" select="@publicID"/>
|
||||
</xsl:call-template>
|
||||
</xsl:attribute>
|
||||
</xsl:if>
|
||||
<xsl:apply-templates/>
|
||||
</xsl:element>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Converts and returns value of an id node -->
|
||||
<xsl:template name="valueOfIDNode">
|
||||
<xsl:call-template name="convertOptionalID">
|
||||
<xsl:with-param name="id" select="string(.)"/>
|
||||
</xsl:call-template>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Converts a scs id to a quakeml id. If the scs id is not set
|
||||
the constant 'NA' is used -->
|
||||
<xsl:template name="convertOptionalID">
|
||||
<xsl:param name="id"/>
|
||||
<xsl:choose>
|
||||
<xsl:when test="$id">
|
||||
<xsl:call-template name="convertID">
|
||||
<xsl:with-param name="id" select="$id"/>
|
||||
</xsl:call-template>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>
|
||||
<xsl:call-template name="convertID">
|
||||
<!--xsl:with-param name="id" select="concat('NA-', generate-id())"/-->
|
||||
<xsl:with-param name="id" select="'NA'"/>
|
||||
</xsl:call-template>
|
||||
</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:template>
|
||||
|
||||
<!-- Converts a scs id to a quakeml id -->
|
||||
<xsl:template name="convertID">
|
||||
<xsl:param name="id"/>
|
||||
<!-- If the id starts with 'smi:' or 'quakeml:', consider that the id
|
||||
is already well formated -->
|
||||
<xsl:choose>
|
||||
<xsl:when test="starts-with($id, 'smi:')
|
||||
or starts-with($id, 'quakeml:')">
|
||||
<xsl:value-of select="$id"/>
|
||||
</xsl:when>
|
||||
<xsl:otherwise>
|
||||
<xsl:value-of select="concat($ID_PREFIX, translate($id, ' :', '__'))"/>
|
||||
</xsl:otherwise>
|
||||
</xsl:choose>
|
||||
</xsl:template>
|
||||
|
||||
</xsl:stylesheet>
|
Reference in New Issue
Block a user