2009-03-13 8 views
12

У меня есть XML с метками времени, как это:Как преобразовать тики в читаемое datetime с XSLT?

<node stamp="1236888746689" /> 

И я хотел бы, чтобы отобразить их в результирующем HTML как дата со временем. Есть ли способ сделать это с помощью XSLT (любая версия)?

EDIT: Я использую XSLT2.0 с Saxon9. Базовая дата - 1970-01-01 0:00.

+0

Технически возможно, но неэффективно и требует дополнительного ввода (например, определение нулевого времени). Я бы выложил это на расширение - какая у вас платформа? – annakata

ответ

13

Вы берете дату 1970-01-01T00:00:00 и добавить столько миллисекунд, как значение штампа говорит вам:

<xsl:stylesheet version="2.0" 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
    xmlns:xs="http://www.w3.org/2001/XMLSchema" 
    xmlns="http://www.w3.org/TR/xhtml1/strict"> 

    <xsl:template match="node"> 
     <xsl:value-of 
select='xs:dateTime("1970-01-01T00:00:00") + @stamp * xs:dayTimeDuration("PT0.001S")'/> 
    </xsl:template> 

</xsl:stylesheet> 
+0

Как изменить ответ на использование внутреннего текста в узле вместо атрибута на нем? – Broam

+0

@Broam Оберните ' '. –

0

XSLT - Turing complete, поэтому должен быть способ. :) Зная хотя бы немного XSLT, это, вероятно, будет включать рекурсию.

Вы не указали точную интерпретацию своих «тиков», я думаю, что миллисекунды с какой-то эпохи, но что? 1970?

1

Если вы хотите использовать XSL 1,0 процессор в том, что не поддерживает EXSLT date and time functions это нетривиальная , но это было сделано.

Вы можете взглянуть на Katy Coe's XSLT 1.0 implementation of the "iso-from-unix" function. Это часть довольно огромного «бесплатного для некоммерческого использования» набора функций даты и времени, которые она создала.

Однако ваш XSL-процессор должен поддерживать пространство имен "http://exslt.org/functions", чтобы эта реализация работала. Кроме того, нет никакой зависимости от EXSLT.

P.S .: Я знаю, что отметка времени и тики Unix не точно то же самое. Тем не менее, они достаточно близки.

8

Если вы используете XSLT 1.0 процессор, который поддерживает EXSLT date functions (я только проверил это с libxslt в PHP), вы можете использовать date:add() и date:duration():

<xsl:value-of select="date:add('1970-01-01T00:00:00Z', date:duration(@stamp div 1000))"/> 

date:duration() функция принимает ряд секунд (так что вам нужно разделить миллисекунды на 1000) и превращает его в «продолжительность» (в этом случае «P14315DT20H12M26.6889998912811S»), который затем добавляется к началу вашей эпохи (выглядит как стандартная эпоха, для этой марки) с date:add(), чтобы получить печать «2009-03-12T20:12:26.6889998912811Z». Затем вы можете отформатировать это, используя функции даты EXSLT, или только substring(), в зависимости от того, что вам нужно.

4

Сказанный ответ, да, я знаю, но я не мог найти тот, который я искал здесь, поэтому я подумал, что заплачу ему за решение.

Мой XML был несколькими узлами, сбрасываемыми с Drupal с использованием export_node и drush. Я использовал xslt-процессор в PHP5, который поддерживает только xslt 1.0. Некоторые функции EXSLT, как представляется, поддерживаются, но я не мог сказать, был ли мой синтаксис неправильным или функция, которую я пыталась использовать, не была поддержана. Во всяком случае, для меня работали. Я использовал код примера из w3schools.com, но добавил строку сразу после объявления xsltprocessor, как показано ниже:

$ xp = new XsltProcessor();
$ xp-> registerPHPFunctions();

PHP имеет тривиальную функцию для преобразования даты, поэтому я обманул и использовал процессор PHP, так как я уже использовал его для преобразования моего xsl.

<xsl:for-each select="node_export/node"> 
    <xsl:value-of select="php:function('date', 'n-j-y', number(timestamp))"/> 
</xsl:for-each> 

Надеюсь, что это поможет кому-то. Я долго стучал головой, когда я работал над этим.

+1

Я также нашел, что мне нужно было использовать это: '' – kenny

 Смежные вопросы

  • Нет связанных вопросов^_^