Changeset 341:7b9ad4f6bf22


Ignore:
Timestamp:
09/17/11 15:19:05 (5 months ago)
Author:
delmitz
Branch:
default
Convert:
svn:7c3792e6-d75b-4784-96a6-b298f655ee64/trunk@2775
Message:

added NtpSyncService.

Location:
kraken-ntp
Files:
2 added
1 deleted
6 edited

Legend:

Unmodified
Added
Removed
  • kraken-ntp/pom.xml

    r308 r341  
    1111        <groupId>org.krakenapps</groupId> 
    1212        <artifactId>kraken-ntp</artifactId> 
    13         <version>1.0.3</version> 
     13        <version>1.1.0</version> 
    1414        <packaging>bundle</packaging> 
    1515        <name>Kraken NTP Client</name> 
     
    6666                </dependency> 
    6767                <dependency> 
     68                        <groupId>org.krakenapps</groupId> 
     69                        <artifactId>kraken-cron</artifactId> 
     70                        <version>1.5.0</version> 
     71                        <optional>true</optional> 
     72                </dependency> 
     73                <dependency> 
    6874                        <groupId>org.apache.felix</groupId> 
    6975                        <artifactId>org.apache.felix.ipojo.annotations</artifactId> 
  • kraken-ntp/src/main/java/org/krakenapps/ntp/NtpClient.java

    r274 r341  
    1717 
    1818import java.io.IOException; 
     19import java.net.DatagramPacket; 
     20import java.net.DatagramSocket; 
    1921import java.net.InetAddress; 
     22import java.net.SocketTimeoutException; 
     23import java.net.UnknownHostException; 
     24import java.text.SimpleDateFormat; 
     25import java.util.Arrays; 
     26import java.util.Calendar; 
    2027import java.util.Date; 
     28 
     29import org.krakenapps.ntp.impl.ServerTime; 
     30import org.slf4j.Logger; 
     31import org.slf4j.LoggerFactory; 
    2132 
    2233/** 
    2334 * @author delmitz 
    2435 */ 
    25 public interface NtpClient { 
    26         InetAddress getTimeServer(); 
    27  
    28         int getTimeout(); 
    29  
    30         void setTimeServer(InetAddress server); 
    31  
    32         void setTimeout(int millisecond); 
    33  
    34         Date sync(); 
    35  
    36         void setSystemTime(Date date) throws IOException; 
     36public class NtpClient { 
     37        private static final String DEFAULT_TIME_SERVER = "pool.ntp.org"; 
     38        private static final int NTP_V3_PACKET = 3; 
     39        private static final int CLIENT_MODE = 3; 
     40        private static final int STRATUM_INDEX = 1; 
     41        private static final int POLL_INDEX = 2; 
     42        private static final int PRECISION_INDEX = 3; 
     43        private static final int ROOT_DELAY_INDEX = 4; 
     44        private static final int ROOT_DISPERSION_INDEX = 8; 
     45        private static final int REFERENCE_IDENTIFIER_INDEX = 12; 
     46        private static final int REFERENCE_TIMESTAMP_INDEX = 16; 
     47        private static final int ORIGINATE_TIMESTAMP_INDEX = 24; 
     48        private static final int RECEIVE_TIMESTAMP_INDEX = 32; 
     49        private static final int TRANSMIT_TIMESTAMP_INDEX = 40; 
     50 
     51        private Logger logger = LoggerFactory.getLogger(NtpClient.class); 
     52 
     53        private InetAddress timeServer; 
     54        private int timeout; 
     55 
     56        public NtpClient() throws UnknownHostException { 
     57                this(null); 
     58        } 
     59 
     60        public NtpClient(String timeServer) throws UnknownHostException { 
     61                this(timeServer, 5000); 
     62        } 
     63 
     64        public NtpClient(String timeServer, int timeout) throws UnknownHostException { 
     65                if (timeServer == null) 
     66                        timeServer = DEFAULT_TIME_SERVER; 
     67                this.timeServer = InetAddress.getByName(timeServer); 
     68                this.timeout = timeout; 
     69        } 
     70 
     71        public InetAddress getTimeServer() { 
     72                return timeServer; 
     73        } 
     74 
     75        public void setTimeServer(InetAddress timeServer) { 
     76                this.timeServer = timeServer; 
     77        } 
     78 
     79        public int getTimeout() { 
     80                return timeout; 
     81        } 
     82 
     83        public void setTimeout(int timeout) { 
     84                this.timeout = timeout; 
     85        } 
     86 
     87        public void setSystemTime(Date time) throws IOException { 
     88                String os = System.getProperty("os.name"); 
     89                if (os.contains("Windows")) { 
     90                        String newDate = new SimpleDateFormat("MM-dd-yy").format(time); 
     91                        Runtime.getRuntime().exec("cmd /c date " + newDate); 
     92 
     93                        String newTime = new SimpleDateFormat("HH:mm:ss.SSS").format(time); 
     94                        newTime = newTime.substring(0, newTime.length() - 1); 
     95                        Runtime.getRuntime().exec("cmd /c time " + newTime); 
     96                } else if (os.contains("Linux")) { 
     97                        String newTime = new SimpleDateFormat("MMddHHmmyyyy.ss").format(time); 
     98                        Runtime.getRuntime().exec("date " + newTime); 
     99                } else { 
     100                        // just pray 
     101                        String newTime = new SimpleDateFormat("MMddHHmmyyyy.ss").format(time); 
     102                        Runtime.getRuntime().exec("date " + newTime); 
     103                } 
     104        } 
     105 
     106        public Date sync() { 
     107                try { 
     108                        ServerTime time = getTime(); 
     109                        setSystemTime(addOffset(time)); 
     110                        logger.info("kraken ntp: The time has been successfully synchronized with {} on {}", timeServer, 
     111                                        new SimpleDateFormat("yyyy/MM/dd HH:mm:ss.SSS 'UTC'").format(time.getTransmit())); 
     112                        return time.getTransmit(); 
     113                } catch (SocketTimeoutException e) { 
     114                        logger.error("kraken ntp: receive timeout.", e); 
     115                } catch (IOException e) { 
     116                        logger.error("kraken ntp: sync failed.", e); 
     117                } 
     118 
     119                return null; 
     120        } 
     121 
     122        private ServerTime getTime() throws IOException { 
     123                DatagramSocket socket = new DatagramSocket(); 
     124                socket.setSoTimeout(timeout); 
     125                transmit(socket, timeServer, 123); 
     126                ServerTime time = receive(socket); 
     127                time.setDestination(getUtcTimeMillis()); 
     128                return time; 
     129        } 
     130 
     131        private void transmit(DatagramSocket socket, InetAddress addr, int port) throws IOException { 
     132                byte[] buf = new byte[48]; 
     133                buf[0] |= NTP_V3_PACKET; // set NTP Packet version 3 
     134                buf[0] |= (CLIENT_MODE << 3); // set Client mode 
     135 
     136                long now = getUtcTimeMillis(); 
     137                now += 2209021200000L; // baseline 1970 to 1900 
     138 
     139                long l = (now / 1000) << 32; 
     140                l |= ((now % 1000) << 32) / 1000; 
     141                for (int i = 7; i >= 0; i--) { // set Transmit Timestamp 
     142                        buf[TRANSMIT_TIMESTAMP_INDEX + i] = (byte) (l & 0xff); 
     143                        l >>>= 8; 
     144                } 
     145 
     146                DatagramPacket p = new DatagramPacket(buf, buf.length); 
     147                p.setAddress(addr); 
     148                p.setPort(port); 
     149                socket.send(p); 
     150        } 
     151 
     152        private long getUtcTimeMillis() { 
     153                return System.currentTimeMillis() - Calendar.getInstance().getTimeZone().getOffset(0); 
     154        } 
     155 
     156        private ServerTime receive(DatagramSocket socket) throws IOException, SocketTimeoutException { 
     157                byte[] buf = new byte[48]; 
     158                DatagramPacket p = new DatagramPacket(buf, buf.length); 
     159                socket.receive(p); 
     160 
     161                ServerTime time = new ServerTime(); 
     162                time.setStratum((int) buf[STRATUM_INDEX]); 
     163                time.setPoll(buf[POLL_INDEX]); 
     164                time.setPrecision(buf[PRECISION_INDEX]); 
     165                time.setRootDelay(Arrays.copyOfRange(buf, ROOT_DELAY_INDEX, ROOT_DELAY_INDEX + 4)); 
     166                time.setRootDispersion(Arrays.copyOfRange(buf, ROOT_DISPERSION_INDEX, ROOT_DISPERSION_INDEX + 4)); 
     167                time.setReferenceIdentifier(Arrays.copyOfRange(buf, REFERENCE_IDENTIFIER_INDEX, REFERENCE_IDENTIFIER_INDEX + 4)); 
     168                time.setReference(ntpTimeToJavaDate(buf, REFERENCE_TIMESTAMP_INDEX)); 
     169                time.setOriginate(ntpTimeToJavaDate(buf, ORIGINATE_TIMESTAMP_INDEX)); 
     170                time.setReceive(ntpTimeToJavaDate(buf, RECEIVE_TIMESTAMP_INDEX)); 
     171                time.setTransmit(ntpTimeToJavaDate(buf, TRANSMIT_TIMESTAMP_INDEX)); 
     172 
     173                return time; 
     174        } 
     175 
     176        private long ntpTimeToJavaDate(byte[] buf, int offset) { 
     177                long seconds = 0; 
     178                for (int i = 0; i < 4; i++) { 
     179                        seconds = seconds << 8; 
     180                        seconds |= buf[offset + i] & 0xff; 
     181                } 
     182                seconds *= 1000L; 
     183                seconds -= 2209021200000L; // baseline 1900 to 1970 
     184 
     185                long fraction = 0; 
     186                for (int i = 4; i < 8; i++) { 
     187                        fraction = fraction << 8; 
     188                        fraction |= buf[offset + i] & 0xff; 
     189                } 
     190                fraction *= 1000; 
     191                fraction >>>= 32; 
     192 
     193                return (seconds + fraction); 
     194        } 
     195 
     196        private Date addOffset(ServerTime time) { 
     197                long millis = System.currentTimeMillis() + time.getClockOffset(); 
     198                return new Date(millis); 
     199        } 
    37200} 
  • kraken-ntp/src/main/java/org/krakenapps/ntp/msgbus/NtpPlugin.java

    r274 r341  
    3030import org.krakenapps.msgbus.handler.MsgbusMethod; 
    3131import org.krakenapps.msgbus.handler.MsgbusPlugin; 
    32 import org.krakenapps.ntp.NtpClient; 
     32import org.krakenapps.ntp.NtpSyncService; 
    3333 
    3434/** 
     
    3939public class NtpPlugin { 
    4040        @Requires 
    41         private NtpClient ntpClient; 
     41        private NtpSyncService syncService; 
    4242 
    4343        @MsgbusMethod 
     
    4848        @MsgbusMethod 
    4949        public void getNtpClientConfig(Request req, Response resp) { 
    50                 resp.put("time_server", ntpClient.getTimeServer().getHostName()); 
    51                 resp.put("timeout", ntpClient.getTimeout()); 
     50                resp.put("time_server", syncService.getTimeServer().getHostName()); 
     51                resp.put("timeout", syncService.getTimeout()); 
    5252        } 
    5353 
     
    5757                int timeout = req.getInteger("timeout"); 
    5858                try { 
    59                         ntpClient.setTimeServer(InetAddress.getByName(server)); 
    60                         ntpClient.setTimeout(timeout); 
     59                        syncService.setTimeServer(InetAddress.getByName(server)); 
     60                        syncService.setTimeout(timeout); 
    6161                } catch (UnknownHostException e) { 
    6262                        throw new MsgbusException("ntp", "unknown host"); 
     
    6666        @MsgbusMethod 
    6767        public void sync(Request req, Response resp) { 
    68                 resp.put("synced_time", ntpClient.sync()); 
     68                resp.put("synced_time", syncService.getNtpClient().sync()); 
    6969        } 
    7070 
     
    8080                try { 
    8181                        Date d = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").parse(s); 
    82                         ntpClient.setSystemTime(d); 
     82                        syncService.getNtpClient().setSystemTime(d); 
    8383                } catch (ParseException e) { 
    8484                        throw new MsgbusException("ntp", "date parse exception"); 
  • kraken-ntp/src/main/java/org/krakenapps/ntp/script/NtpScript.java

    r274 r341  
    2525import org.krakenapps.api.ScriptContext; 
    2626import org.krakenapps.api.ScriptUsage; 
    27 import org.krakenapps.ntp.NtpClient; 
     27import org.krakenapps.ntp.NtpSyncService; 
    2828 
    2929/** 
     
    3232public class NtpScript implements Script { 
    3333        private ScriptContext context; 
    34         private NtpClient ntpClient; 
     34        private NtpSyncService syncService; 
    3535 
    36         public NtpScript(NtpClient ntpClient) { 
    37                 this.ntpClient = ntpClient; 
     36        public NtpScript(NtpSyncService syncService) { 
     37                this.syncService = syncService; 
    3838        } 
    3939 
     
    4949                        try { 
    5050                                InetAddress server = InetAddress.getByName(args[0]); 
    51                                 ntpClient.setTimeServer(server); 
     51                                syncService.setTimeServer(server); 
    5252                        } catch (UnknownHostException e) { 
    5353                                context.println("unknown host"); 
     
    5555                } 
    5656 
    57                 context.println(ntpClient.getTimeServer()); 
     57                context.println(syncService.getTimeServer()); 
    5858        } 
    5959 
     
    6363                if (args.length > 0) { 
    6464                        Integer millisecond = Integer.parseInt(args[0]); 
    65                         ntpClient.setTimeout(millisecond); 
     65                        syncService.setTimeout(millisecond); 
    6666                } 
    6767 
    68                 context.println(ntpClient.getTimeout()); 
     68                context.println(syncService.getTimeout()); 
    6969        } 
    7070 
    7171        public void sync(String[] args) { 
    72                 Date result = ntpClient.sync(); 
     72                Date result = syncService.getNtpClient().sync(); 
    7373                if (result != null) 
    74                         context.printf("The time has been successfully synchronized with %s on %s\n", ntpClient.getTimeServer() 
     74                        context.printf("The time has been successfully synchronized with %s on %s\n", syncService.getTimeServer() 
    7575                                        .getHostName(), new SimpleDateFormat("yyyy/MM/dd HH:mm:ss.SSS 'UTC'").format(result)); 
    7676                else 
  • kraken-ntp/src/main/java/org/krakenapps/ntp/script/NtpScriptFactory.java

    r2 r341  
    2222import org.krakenapps.api.Script; 
    2323import org.krakenapps.api.ScriptFactory; 
    24 import org.krakenapps.ntp.NtpClient; 
     24import org.krakenapps.ntp.NtpSyncService; 
    2525 
    2626/** 
     
    3535 
    3636        @Requires 
    37         private NtpClient ntpClient; 
     37        private NtpSyncService syncService; 
    3838 
    3939        @Override 
    4040        public Script createScript() { 
    41                 return new NtpScript(ntpClient); 
     41                return new NtpScript(syncService); 
    4242        } 
    4343 
  • kraken-ntp/src/main/resources/metadata.xml

    r2 r341  
    22        xsi:schemaLocation="org.apache.felix.ipojo http://felix.apache.org/ipojo/schemas/CURRENT/core.xsd" 
    33        xmlns="org.apache.felix.ipojo"> 
    4         <instance component="ntp-client" /> 
     4        <instance component="ntp-sync-service" /> 
    55        <instance component="ntp-script-factory" /> 
    66        <instance component="ntp-plugin" /> 
Note: See TracChangeset for help on using the changeset viewer.