2012-05-02 7 views
5

Ho una intranet in esecuzione su una casella Linux, che autentica contro Active Directory su una casella di Windows, utilizzando LDAP tramite PHP.Convertire la data/ora di Windows con PHP su una Linux Box

posso recuperare la voce di un utente da AD utilizzando LDAP e accedere l'ultima data di accesso dal esempio array PHP:

echo $adAccount['lastlogontimestamp'][0]; // returns something like 129802528752492619 

Se questo fosse un timestamp Unix Vorrei utilizzare il seguente codice PHP da convertire in un data leggibile dall'uomo:

date("d-m-Y H:i:s", $lastlogontimestamp); 

Tuttavia, questo non funziona. Qualcuno sa come posso ottenere questo o, in effetti, se è possibile farlo da una scatola Linux?

risposta

10

Secondo this, il timestamp di Windows che hai lì è il numero di 100-ns dal 1 ° gennaio 1601. Pertanto, potresti semplicemente convertirlo in un unico x timestamp utilizzando la seguente formula:

tUnix = tWindow/(10*1000*1000)-11644473600; 

È dividere per 10*1000*1000 per convertire in secondi dal 1 gennaio 1601 e quindi lo sconto 11644473600 che è il numero di secondi tra gennaio 1601 e gennaio 1970 (tempo di Unix).

Così in PHP:

date("d-m-Y H:i:s", $lastlogontimestamp/10000000-11644473600); 

EDIT: È interessante notare, ho avuto un offset di Baba diversa. Ho ottenuto il mio con Java:

Calendar date1 = Calendar.getInstance(); date1.set(1601, 1, 1); 
Calendar date2 = Calendar.getInstance(); date2.set(1970, 1, 1); 
long dt = date2.getTimeInMillis() - date1.getTimeInMillis(); 
System.out.println(String.format("%f", dt/1000.0)); // prints "11644473600.000000" 

Secondo questo SO: Ways to Convert Unix/Linux time to Windows time compensare mio è corretto.

+3

Ho ottenuto un offset diverso con PHP: strtotime ("1601-01-01") - strtotime ("1970-01-01") = 11644470000. Questa è un'ora (3600 secondi) diversa dalla tua, ma come MSDN dice che per usare il valore derivato Java userò la tua risposta. Grazie per l'assistenza e grazie a Baba. – amburnside

+1

Ho anche visto 11644477200 (come usato da Baba). Questo è almeno tre diversi valori. Certo, la differenza non è enorme e potrebbe non essere rilevante in alcuni contesti, ma è bene sapere qual è il valore corretto da sottrarre, indipendentemente dal fuso orario. Vado con il valore "... 7360 ..." come [visto nel MSDN] (http://msdn.microsoft.com/en-us/library/ms724228). – Synetech

+0

@Synetech Sì, l'intera faccenda della data è un casino sanguinoso. Dipende sempre da quale sistema stai usando. – brimborium

3

Poiché Windows non è in secondi, ma in nano seconds è necessario arrotondare in su dividendolo per 10000000 è anche necessario rimuovere secondi tra 1601-01-01 and 1970-01-01 fin dall'inizio finestre timestamp da 1601-01-01

function convertWindowsTimestamp($wintime) { 
    return $wintime/10000000 - 11644477200; 
} 

$lastlogontimestamp = convertWindowsTimestamp("129802528752492619"); 
$date = date("d-m-Y H:i:s", $lastlogontimestamp); 
var_dump($date); 

uscita

string '30-04-2012 10:47:55' (length=19) 
+0

Puoi spiegare cosa sta facendo la tua funzione cioè, perché dividere per 10 milioni e quindi sottrarre 11644477200? – amburnside

+0

ha aggiunto l'esplorazione – Baba

Problemi correlati