2013-03-21 22 views
11

Wiem, że jest to dość powszechne pytanie, ale nie wydaje mi się, że odpowiedzi, które znalazłem, naprawdę rozwiązują problem. Przedstawię mój konkretny przypadek użycia i przedstawię podsumowania informacji z innych odpowiedzi SO oraz z internetu.Znaczniki czasu: iso8601 vs unix timestamp

Dla usługi, którą piszę, wpisy w bazie danych są tworzone i przechowywane zarówno na urządzeniach mobilnych, jak i na naszej stronie internetowej i muszą być zsynchronizowane w obie strony. Obecnie kierujemy reklamy na Androida i iOS, które używają sqlite jako relacyjnej bazy danych. Strona serwera jest zaimplementowana w Pythonie przy użyciu Django z MySQL, ale inne rozwiązania mogą zastąpić to w przyszłości.

Synchronizacja zostanie wdrożona zgodnie z ideami opisanymi w tej odpowiedzi na to pytanie: https://stackoverflow.com/a/5052208/2076094. Do synchronizacji użyjemy znacznika czasu, który jest ustawiony tylko przez serwer i zsynchronizowany z klientami, last_synced_date i znacznikami czasu dla tworzenia i aktualizacji obiektu. Ponieważ obiekty odnoszą się do czegoś, co zrobił użytkownik w określonym czasie, mają również informację o znaczniku czasu.

Moje pytanie dotyczy tylko wewnętrznego przedstawienia czasu używanego dla tych znaczników czasowych. Reprezentacja użytkownika w interfejsie użytkownika jest zlokalizowaną i sformatowaną wersją reprezentacji wewnętrznej. Istnieje wiele różnych sposobów zarówno w językach implementacyjnych, jak iw różnych bazach danych używanych do reprezentowania znaczników czasu. Po całkiem sporo badań wydaje się, że tylko do prawidłowych rozwiązań lewej:

  • Unix czas
  • ISO8601

Ten article który był na Hacker News (dwukrotnie) sugeruje użycie czas uniksowy i przedstawia całkiem dobry argument. Dyskusja na temat HN, jak można się spodziewać, różni się nieco wokół dwóch punktów opisanych powyżej, a następnie niektórych.

Moja dotychczasowa konkluzja jest taka, że ​​sygnatury czasowe uniksowe są łatwiejsze w obsłudze, ale nie wydają się być popularnym sposobem w Django. Prawie każdy przykład kodu, jaki znalazłem, od samouczka Django do wielu innych stron, używa DateTimeField w models.py, który jest mapowany do pewnego rodzaju pola daty w SQL, dokładne warunki w zależności od używanej bazy danych.

Wadą stosowania dat transmisji w standardzie ISO8601 jest to, że należy je przeanalizować, aby utworzyć typ daty odpowiedniego języka implementacji. To nie jest trudne, ale trochę denerwujące. Dla każdego używanego języka potrzebujesz albo (małej) biblioteki albo przynajmniej więcej kodu, niż byś miał nadzieję. Nie jest bardzo ładny, tworzy zależności i jest prawdopodobnie nieco wolniejszy. Uniksowe znaczniki czasu nie mają tego problemu w żadnym znanym mi lance.

Inną sprawą jest to, że można łatwo popaść w kłopoty za pomocą "inteligentnych" pól dat lub datowników w bazie danych (i podczas parsowania). Istnieje wiele pytań dotyczących SO, związanych z magią czasu, która rozwiązuje problem. Osiągnięto limit moich linków, więc nie mogę ich opublikować, ale łatwo je znajdziesz;)

Możemy użyć uproszczonego formatu, który nie zawiera informacji o strefie czasowej i zawsze używaj zawsze UTC. W każdym razie używamy tylko UTC, ale wydaje się, że jeśli używasz ISO8601, równie dobrze możesz użyć formatu, który jest powszechnie zrozumiały i jednoznaczny. Unix-time jest zawsze w UTC, więc nigdy nie musisz się o to martwić.

Oczywiście, ISO8601 ma tę zaletę, że można go odczytać jako człowieka, gdy patrzy się na surową bazę danych i nie będę musiał przepisywać kilku linii kodu tuż przed 2038, ale to nie wydaje się rekompensować wady.

Wygląda na to, że pisząc rzeczy, faktycznie mam już odpowiedź;) W każdym razie, chciałbym wiedzieć, co myślą inni i co robicie w swoich własnych projektach. Podaj krótki zarys swojego przypadku użycia, aby inni mogli lepiej klasyfikować Twoje dane wejściowe.

Dzięki!

Odpowiedz

0

dziękuję za to wspaniałe pytanie postawione na stole. Naprawdę trudno jest znaleźć jakiekolwiek informacje na temat typów danych czasowych lub standardów/formatów czasu, niezależnie od tego, jak się to nazywa. Przez ostatnie kilka dni zmagałem się, by wybrać odpowiedni format czasu. Będę kodować zarówno na urządzeniach mobilnych, jak i na serwerze sieciowym (nie wspominając już o aplikacji na komputery). Moje umiejętności techniczne są raczej empiryczne, moje studium tła jest sztuką, ale dość często pracuję z kodowaniem. I główne pytanie, które zadawałem sobie, brzmiał: "w jaki sposób mogę mieć bezproblemowe doświadczenie między urządzeniem mobilnym, serwerem sieciowym (API lub jakkolwiek to nazwać) a aplikacją na komputer? Jak można zachować spójność w przypadku wystąpienia zdarzenia? i jak upewnić się, że reprezentacja tej chwili jest taka sama na różnych poziomach tej konstelacji oprogramowania?

Jak wiadomo, kodowanie za pomocą urządzeń mobilnych oznacza, że ​​korzystasz z baz danych SQLite, a aplikacje internetowe w większości wymagają MySQL. głęboko rozczarowany faktem, że jednym z największych bólów głowy, jakie mogłem sobie wyobrazić, było przechodzenie od jednej tabeli do drugiej z danymi czasowymi, co wybrać? DateTime? Timestamp? Oh gosh, SQLite nie ma wbudowanego typu danych w czasie ... Czas Unix? Ok, nie ma problemu, oczywiście MySQL nie używa czasu UNIX jako standard ... Byłby zbyt prosty ...

Dowiedziałem się, że ... Jeśli chcesz umieścić dane na osi czasu i powiedzieć, że jest to punkt na osi czasu, w którym wydarzenie to miało miejsce, użyj znaczników czasu (czy to w stylu UNIX czy MySQL, jak ISO8601). Czytelność dla człowieka jest dla mnie tylko szczegółem. Żaden człowiek nie powinien odczytywać tabel bazy danych, komputery robią, a ty mówisz komputerowi, żeby obsługiwał dane, aby ludzie mogli to zrozumieć. Ale potem pytanie "jaka jest strefa czasowa?" wyskoczył ... Cóż ... to jest do bani ... Ale hej, przekopie sieć w poszukiwaniu odpowiedzi.

Sam jestem zaskoczony, że MySQL nie jest czasem UNIX-a, uważam, że jest to najbardziej standardowy i spójny czas, jaki można mieć.

Naprawdę uważam, że dokumentacja dotycząca tego problemu jest bardziej niż lekka ... Zastanawiam się nad napisaniem artykułu o tym, jak poradzić sobie z MySQL i SQLite. W tej sprawie naprawdę zmarnowałem 3 dni, próbując zrozumieć, jak zrobić to czystym i prostym. Mój wniosek z dostępnej dokumentacji po prostu nie można ...: PI jestem prawdopodobnie źle ... Tak czy inaczej, warto spojrzeć na ten film pokazujący zmagania z obsługi danych czasowych na MySQL: http://www.youtube.com/watch?v=fp-etlirjbo

Dzięki za komentarz na to pytanie, to było dla mnie całkiem pouczające.

Cheers,

Ben

+2

Zawsze używaj UTC dla strefy czasowej i konwertować do czasu lokalnego, kiedy trzeba czasu lokalnego. –

+1

@AnthonyHunt .... Dlaczego? Czas Unix to liczba. * jego wartość jest zawsze GMT * jest dużo krótszy (unix timestamp wymaga 32 bitową liczbę całkowitą, gdy znaczniki czasu wymaga 200 bitów ASCII) * to platforma/język agnostykiem i obsługiwane przez wszystkich języków programowania * 64 bitowych systemów operacyjnych wykorzystujących 64-bitowa t_czasowa liczba całkowita, więc będzie trwać śmierć ciepła wszechświata Więc jestem naprawdę ciekawy, dlaczego zdecydowałbyś się poświęcić mobilność, rozmiar i podatność na parsowanie ciągów? – Ancarius