Advertisement
Guest User

Untitled

a guest
Jul 8th, 2021
152
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Java 29.38 KB | None | 0 0
  1. /*******************************************************************************
  2.  * Copyright (c) 2013-2015 Sierra Wireless and others.
  3.  *
  4.  * All rights reserved. This program and the accompanying materials
  5.  * are made available under the terms of the Eclipse Public License v2.0
  6.  * and Eclipse Distribution License v1.0 which accompany this distribution.
  7.  *
  8.  * The Eclipse Public License is available at
  9.  *    http://www.eclipse.org/legal/epl-v20.html
  10.  * and the Eclipse Distribution License is available at
  11.  *    http://www.eclipse.org/org/documents/edl-v10.html.
  12.  *
  13.  * Contributors:
  14.  *     Sierra Wireless - initial API and implementation
  15.  *     Achim Kraus (Bosch Software Innovations GmbH) - use Identity as destination
  16.  *******************************************************************************/
  17. package org.eclipse.leshan.server.registration;
  18.  
  19. import java.net.InetAddress;
  20. import java.net.InetSocketAddress;
  21. import java.util.Arrays;
  22. import java.util.Collections;
  23. import java.util.Comparator;
  24. import java.util.Date;
  25. import java.util.EnumSet;
  26. import java.util.HashMap;
  27. import java.util.HashSet;
  28. import java.util.Map;
  29. import java.util.Set;
  30. import java.util.TreeSet;
  31.  
  32. import org.eclipse.leshan.core.Link;
  33. import org.eclipse.leshan.core.LwM2m.Version;
  34. import org.eclipse.leshan.core.attributes.Attribute;
  35. import org.eclipse.leshan.core.model.ObjectModel;
  36. import org.eclipse.leshan.core.node.LwM2mPath;
  37. import org.eclipse.leshan.core.request.BindingMode;
  38. import org.eclipse.leshan.core.request.ContentFormat;
  39. import org.eclipse.leshan.core.request.Identity;
  40. import org.eclipse.leshan.core.util.StringUtils;
  41. import org.eclipse.leshan.core.util.Validate;
  42. import org.eclipse.leshan.server.security.Authorizer;
  43. import org.slf4j.Logger;
  44. import org.slf4j.LoggerFactory;
  45.  
  46. /**
  47.  * An immutable structure which represent a LW-M2M client registration on the server
  48.  */
  49. public class Registration {
  50.  
  51.     private static final Logger LOG = LoggerFactory.getLogger(Registration.class);
  52.  
  53.     private static final long DEFAULT_LIFETIME_IN_SEC = 86400L;
  54.  
  55.     private final Date registrationDate;
  56.  
  57.     private final Identity identity;
  58.  
  59.     private final long lifeTimeInSec;
  60.  
  61.     private final String smsNumber;
  62.  
  63.     private final Version lwM2mVersion;
  64.  
  65.     private final EnumSet<BindingMode> bindingMode;
  66.  
  67.     private final Boolean queueMode; // since LWM2M 1.1
  68.  
  69.     // The LWM2M Client's unique end point name.
  70.     private final String endpoint;
  71.  
  72.     private final String id;
  73.  
  74.     private final Link[] objectLinks;
  75.  
  76.     private final Map<String, String> additionalRegistrationAttributes;
  77.  
  78.     // The location where LWM2M objects are hosted on the device
  79.     private final String rootPath;
  80.  
  81.     // All ContentFormat supported by the client
  82.     private final Set<ContentFormat> supportedContentFormats;
  83.  
  84.     // All supported object (object id => version)
  85.     private final Map<Integer, String> supportedObjects;
  86.  
  87.     // All available instances
  88.     private final Set<LwM2mPath> availableInstances;
  89.  
  90.     private final Date lastUpdate;
  91.  
  92.     private final Map<String, String> applicationData;
  93.  
  94.     protected Registration(Builder builder) {
  95.  
  96.         Validate.notNull(builder.registrationId);
  97.         Validate.notEmpty(builder.endpoint);
  98.         Validate.notNull(builder.identity);
  99.  
  100.         // mandatory params
  101.         id = builder.registrationId;
  102.         identity = builder.identity;
  103.         endpoint = builder.endpoint;
  104.  
  105.         // object links related params
  106.         objectLinks = builder.objectLinks;
  107.         rootPath = builder.rootPath;
  108.         supportedContentFormats = builder.supportedContentFormats;
  109.         supportedObjects = builder.supportedObjects;
  110.         availableInstances = builder.availableInstances;
  111.  
  112.         // other params
  113.         lifeTimeInSec = builder.lifeTimeInSec;
  114.         lwM2mVersion = builder.lwM2mVersion;
  115.         bindingMode = builder.bindingMode;
  116.         queueMode = builder.queueMode;
  117.         registrationDate = builder.registrationDate;
  118.         lastUpdate = builder.lastUpdate;
  119.         smsNumber = builder.smsNumber;
  120.         additionalRegistrationAttributes = builder.additionalRegistrationAttributes;
  121.  
  122.         applicationData = builder.applicationData;
  123.     }
  124.  
  125.     public String getId() {
  126.         return id;
  127.     }
  128.  
  129.     public Date getRegistrationDate() {
  130.         return registrationDate;
  131.     }
  132.  
  133.     /**
  134.      * Gets the clients identity.
  135.      *
  136.      * @return identity from client's most recent registration or registration update.
  137.      */
  138.     public Identity getIdentity() {
  139.         return identity;
  140.     }
  141.  
  142.     /**
  143.      * Gets the client's network socket address.
  144.      *
  145.      * @return the source address from the client's most recent CoAP message.
  146.      */
  147.     public InetSocketAddress getSocketAddress() {
  148.         return identity.getPeerAddress();
  149.     }
  150.  
  151.     /**
  152.      * Gets the client's network address.
  153.      *
  154.      * @return the source address from the client's most recent CoAP message.
  155.      */
  156.     public InetAddress getAddress() {
  157.         return identity.getPeerAddress().getAddress();
  158.     }
  159.  
  160.     /**
  161.      * Gets the client's network port number.
  162.      *
  163.      * @return the source port from the client's most recent CoAP message.
  164.      */
  165.     public int getPort() {
  166.         return identity.getPeerAddress().getPort();
  167.     }
  168.  
  169.     public Link[] getObjectLinks() {
  170.         return objectLinks;
  171.     }
  172.  
  173.     public Link[] getSortedObjectLinks() {
  174.         // sort the list of objects
  175.         if (objectLinks == null) {
  176.             return null;
  177.         }
  178.  
  179.         Link[] res = Arrays.copyOf(objectLinks, objectLinks.length);
  180.  
  181.         Arrays.sort(res, new Comparator<Link>() {
  182.  
  183.             /* sort by path */
  184.             @Override
  185.             public int compare(Link o1, Link o2) {
  186.                 if (o1 == null && o2 == null)
  187.                     return 0;
  188.                 if (o1 == null)
  189.                     return -1;
  190.                 if (o2 == null)
  191.                     return 1;
  192.                 // by URL
  193.                 String[] url1 = o1.getUrl().split("/");
  194.                 String[] url2 = o2.getUrl().split("/");
  195.  
  196.                 for (int i = 0; i < url1.length && i < url2.length; i++) {
  197.                     // is it two numbers?
  198.                     if (isNumber(url1[i]) && isNumber(url2[i])) {
  199.                         int cmp = Integer.parseInt(url1[i]) - Integer.parseInt(url2[i]);
  200.                         if (cmp != 0) {
  201.                             return cmp;
  202.                         }
  203.                     } else {
  204.  
  205.                         int v = url1[i].compareTo(url2[i]);
  206.  
  207.                         if (v != 0) {
  208.                             return v;
  209.                         }
  210.                     }
  211.                 }
  212.  
  213.                 return url1.length - url2.length;
  214.             }
  215.         });
  216.  
  217.         return res;
  218.     }
  219.  
  220.     private static boolean isNumber(String s) {
  221.         return !StringUtils.isEmpty(s) && StringUtils.isNumeric(s);
  222.     }
  223.  
  224.     public Long getLifeTimeInSec() {
  225.         return lifeTimeInSec;
  226.     }
  227.  
  228.     public String getSmsNumber() {
  229.         return smsNumber;
  230.     }
  231.  
  232.     public Version getLwM2mVersion() {
  233.         return lwM2mVersion;
  234.     }
  235.  
  236.     public EnumSet<BindingMode> getBindingMode() {
  237.         return bindingMode;
  238.     }
  239.  
  240.     public Boolean getQueueMode() {
  241.         return queueMode;
  242.     }
  243.  
  244.     /**
  245.      * @return the path where the objects are hosted on the device
  246.      */
  247.     public String getRootPath() {
  248.         return rootPath;
  249.     }
  250.  
  251.     /**
  252.      * @return all {@link ContentFormat} supported by the client.
  253.      */
  254.     public Set<ContentFormat> getSupportedContentFormats() {
  255.         return supportedContentFormats;
  256.     }
  257.  
  258.     /**
  259.      * @return all available object instance by the client
  260.      */
  261.     public Set<LwM2mPath> getAvailableInstances() {
  262.         return availableInstances;
  263.     }
  264.  
  265.     /**
  266.      * Gets the unique name the client has registered with.
  267.      *
  268.      * @return the name
  269.      */
  270.     public String getEndpoint() {
  271.         return endpoint;
  272.     }
  273.  
  274.     public Date getLastUpdate() {
  275.         return lastUpdate;
  276.     }
  277.  
  278.     public long getExpirationTimeStamp() {
  279.         return getExpirationTimeStamp(0L);
  280.     }
  281.  
  282.     public long getExpirationTimeStamp(long gracePeriodInSec) {
  283.         return lastUpdate.getTime() + lifeTimeInSec * 1000 + gracePeriodInSec * 1000;
  284.     }
  285.  
  286.     /**
  287.      * @return True if DTLS handshake can be initiated by the Server for this registration.
  288.      */
  289.     public boolean canInitiateConnection() {
  290.         // We consider that initiates a connection (acting as DTLS client to initiate a handshake) does not make sense
  291.         // for QueueMode as if we lost connection device is probably absent.
  292.         return !usesQueueMode();
  293.     }
  294.  
  295.     /**
  296.      * @return true if the last registration update was done less than lifetime seconds ago.
  297.      */
  298.     public boolean isAlive() {
  299.         return isAlive(0);
  300.     }
  301.  
  302.     /**
  303.      * This is the same idea than {@link Registration#isAlive()} but with a grace period. <br>
  304.      *
  305.      * @param gracePeriodInSec an extra time for the registration lifetime.
  306.      * @return true if the last registration update was done less than lifetime+gracePeriod seconds ago.
  307.      */
  308.     public boolean isAlive(long gracePeriodInSec) {
  309.         return getExpirationTimeStamp(gracePeriodInSec) > System.currentTimeMillis();
  310.     }
  311.  
  312.     public Map<String, String> getAdditionalRegistrationAttributes() {
  313.         return additionalRegistrationAttributes;
  314.     }
  315.  
  316.     public boolean usesQueueMode() {
  317.         if (lwM2mVersion.olderThan(Version.V1_1))
  318.             return bindingMode.contains(BindingMode.Q);
  319.         else
  320.             return queueMode;
  321.     }
  322.  
  323.     /**
  324.      * @param objectid the object id for which we want to know the supported version.
  325.      * @return the supported version of the object with the id {@code objectid}. If the object is not supported return
  326.      *         {@code null}
  327.      */
  328.     public String getSupportedVersion(Integer objectid) {
  329.         return getSupportedObject().get(objectid);
  330.     }
  331.  
  332.     /**
  333.      * @return a map from {@code objectId} {@literal =>} {@code supportedVersion} for each supported objects. supported.
  334.      */
  335.     public Map<Integer, String> getSupportedObject() {
  336.         return supportedObjects;
  337.     }
  338.  
  339.     /**
  340.      * @return Some application data which could have been added at Registration by the {@link Authorizer}
  341.      */
  342.     public Map<String, String> getApplicationData() {
  343.         return applicationData;
  344.     }
  345.  
  346.     @Override
  347.     public String toString() {
  348.         return String.format(
  349.                 "Registration [registrationDate=%s, identity=%s, lifeTimeInSec=%s, smsNumber=%s, lwM2mVersion=%s, bindingMode=%s, queueMode=%s, endpoint=%s, id=%s, objectLinks=%s, additionalRegistrationAttributes=%s, rootPath=%s, supportedContentFormats=%s, supportedObjects=%s, availableInstances=%s, lastUpdate=%s, applicationData=%s]",
  350.                 registrationDate, identity, lifeTimeInSec, smsNumber, lwM2mVersion, bindingMode, queueMode, endpoint,
  351.                 id, Arrays.toString(objectLinks), additionalRegistrationAttributes, rootPath, supportedContentFormats,
  352.                 supportedObjects, availableInstances, lastUpdate, applicationData);
  353.     }
  354.  
  355.     @Override
  356.     public int hashCode() {
  357.         final int prime = 31;
  358.         int result = 1;
  359.         result = prime * result
  360.                 + ((additionalRegistrationAttributes == null) ? 0 : additionalRegistrationAttributes.hashCode());
  361.         result = prime * result + ((applicationData == null) ? 0 : applicationData.hashCode());
  362.         result = prime * result + ((availableInstances == null) ? 0 : availableInstances.hashCode());
  363.         result = prime * result + ((bindingMode == null) ? 0 : bindingMode.hashCode());
  364.         result = prime * result + ((endpoint == null) ? 0 : endpoint.hashCode());
  365.         result = prime * result + ((id == null) ? 0 : id.hashCode());
  366.         result = prime * result + ((identity == null) ? 0 : identity.hashCode());
  367.         result = prime * result + ((lastUpdate == null) ? 0 : lastUpdate.hashCode());
  368.         result = prime * result + (int) (lifeTimeInSec ^ (lifeTimeInSec >>> 32));
  369.         result = prime * result + ((lwM2mVersion == null) ? 0 : lwM2mVersion.hashCode());
  370.         result = prime * result + Arrays.hashCode(objectLinks);
  371.         result = prime * result + ((queueMode == null) ? 0 : queueMode.hashCode());
  372.         result = prime * result + ((registrationDate == null) ? 0 : registrationDate.hashCode());
  373.         result = prime * result + ((rootPath == null) ? 0 : rootPath.hashCode());
  374.         result = prime * result + ((smsNumber == null) ? 0 : smsNumber.hashCode());
  375.         result = prime * result + ((supportedContentFormats == null) ? 0 : supportedContentFormats.hashCode());
  376.         result = prime * result + ((supportedObjects == null) ? 0 : supportedObjects.hashCode());
  377.         return result;
  378.     }
  379.  
  380.     @Override
  381.     public boolean equals(Object obj) {
  382.         if (this == obj)
  383.             return true;
  384.         if (obj == null)
  385.             return false;
  386.         if (getClass() != obj.getClass())
  387.             return false;
  388.         Registration other = (Registration) obj;
  389.         if (additionalRegistrationAttributes == null) {
  390.             if (other.additionalRegistrationAttributes != null)
  391.                 return false;
  392.         } else if (!additionalRegistrationAttributes.equals(other.additionalRegistrationAttributes))
  393.             return false;
  394.         if (applicationData == null) {
  395.             if (other.applicationData != null)
  396.                 return false;
  397.         } else if (!applicationData.equals(other.applicationData))
  398.             return false;
  399.         if (availableInstances == null) {
  400.             if (other.availableInstances != null)
  401.                 return false;
  402.         } else if (!availableInstances.equals(other.availableInstances))
  403.             return false;
  404.         if (bindingMode == null) {
  405.             if (other.bindingMode != null)
  406.                 return false;
  407.         } else if (!bindingMode.equals(other.bindingMode))
  408.             return false;
  409.         if (endpoint == null) {
  410.             if (other.endpoint != null)
  411.                 return false;
  412.         } else if (!endpoint.equals(other.endpoint))
  413.             return false;
  414.         if (id == null) {
  415.             if (other.id != null)
  416.                 return false;
  417.         } else if (!id.equals(other.id))
  418.             return false;
  419.         if (identity == null) {
  420.             if (other.identity != null)
  421.                 return false;
  422.         } else if (!identity.equals(other.identity))
  423.             return false;
  424.         if (lastUpdate == null) {
  425.             if (other.lastUpdate != null)
  426.                 return false;
  427.         } else if (!lastUpdate.equals(other.lastUpdate))
  428.             return false;
  429.         if (lifeTimeInSec != other.lifeTimeInSec)
  430.             return false;
  431.         if (lwM2mVersion == null) {
  432.             if (other.lwM2mVersion != null)
  433.                 return false;
  434.         } else if (!lwM2mVersion.equals(other.lwM2mVersion))
  435.             return false;
  436.         if (!Arrays.equals(objectLinks, other.objectLinks))
  437.             return false;
  438.         if (queueMode == null) {
  439.             if (other.queueMode != null)
  440.                 return false;
  441.         } else if (!queueMode.equals(other.queueMode))
  442.             return false;
  443.         if (registrationDate == null) {
  444.             if (other.registrationDate != null)
  445.                 return false;
  446.         } else if (!registrationDate.equals(other.registrationDate))
  447.             return false;
  448.         if (rootPath == null) {
  449.             if (other.rootPath != null)
  450.                 return false;
  451.         } else if (!rootPath.equals(other.rootPath))
  452.             return false;
  453.         if (smsNumber == null) {
  454.             if (other.smsNumber != null)
  455.                 return false;
  456.         } else if (!smsNumber.equals(other.smsNumber))
  457.             return false;
  458.         if (supportedContentFormats == null) {
  459.             if (other.supportedContentFormats != null)
  460.                 return false;
  461.         } else if (!supportedContentFormats.equals(other.supportedContentFormats))
  462.             return false;
  463.         if (supportedObjects == null) {
  464.             if (other.supportedObjects != null)
  465.                 return false;
  466.         } else if (!supportedObjects.equals(other.supportedObjects))
  467.             return false;
  468.         return true;
  469.     }
  470.  
  471.     public static class Builder {
  472.         private final String registrationId;
  473.         private final String endpoint;
  474.         private final Identity identity;
  475.  
  476.         private Date registrationDate;
  477.         private Date lastUpdate;
  478.         private Long lifeTimeInSec;
  479.         private String smsNumber;
  480.         private EnumSet<BindingMode> bindingMode;
  481.         private Boolean queueMode;
  482.         private Version lwM2mVersion = Version.getDefault();
  483.         private Link[] objectLinks;
  484.         private String rootPath;
  485.         private Set<ContentFormat> supportedContentFormats;
  486.         private Map<Integer, String> supportedObjects;
  487.         private Set<LwM2mPath> availableInstances;
  488.         private Map<String, String> additionalRegistrationAttributes;
  489.         private Map<String, String> applicationData;
  490.  
  491.         // builder setting
  492.         private boolean extractData; // if true extract data from objectLinks
  493.  
  494.         public Builder(Registration registration) {
  495.  
  496.             // mandatory params
  497.             registrationId = registration.id;
  498.             identity = registration.identity;
  499.             endpoint = registration.endpoint;
  500.  
  501.             // object links related params
  502.             objectLinks = registration.objectLinks;
  503.             rootPath = registration.rootPath;
  504.             supportedContentFormats = registration.supportedContentFormats;
  505.             supportedObjects = registration.supportedObjects;
  506.             availableInstances = registration.availableInstances;
  507.  
  508.             // other params
  509.             lifeTimeInSec = registration.lifeTimeInSec;
  510.             lwM2mVersion = registration.lwM2mVersion;
  511.             bindingMode = registration.bindingMode;
  512.             queueMode = registration.queueMode;
  513.             registrationDate = registration.registrationDate;
  514.             lastUpdate = registration.lastUpdate;
  515.             smsNumber = registration.smsNumber;
  516.             additionalRegistrationAttributes = registration.additionalRegistrationAttributes;
  517.  
  518.             applicationData = registration.applicationData;
  519.         }
  520.  
  521.         public Builder(String registrationId, String endpoint, Identity identity) {
  522.  
  523.             Validate.notNull(registrationId);
  524.             Validate.notEmpty(endpoint);
  525.             Validate.notNull(identity);
  526.             this.registrationId = registrationId;
  527.             this.endpoint = endpoint;
  528.             this.identity = identity;
  529.         }
  530.  
  531.         public Builder extractDataFromObjectLink(boolean extract) {
  532.             this.extractData = extract;
  533.             return this;
  534.         }
  535.  
  536.         public Builder registrationDate(Date registrationDate) {
  537.             this.registrationDate = registrationDate;
  538.             return this;
  539.         }
  540.  
  541.         public Builder lastUpdate(Date lastUpdate) {
  542.             this.lastUpdate = lastUpdate;
  543.             return this;
  544.         }
  545.  
  546.         public Builder lifeTimeInSec(Long lifetimeInSec) {
  547.             this.lifeTimeInSec = lifetimeInSec;
  548.             return this;
  549.         }
  550.  
  551.         public Builder smsNumber(String smsNumber) {
  552.             this.smsNumber = smsNumber;
  553.             return this;
  554.         }
  555.  
  556.         public Builder bindingMode(EnumSet<BindingMode> bindingMode) {
  557.             this.bindingMode = bindingMode;
  558.             return this;
  559.         }
  560.  
  561.         public Builder queueMode(Boolean queueMode) {
  562.             this.queueMode = queueMode;
  563.             return this;
  564.         }
  565.  
  566.         public Builder lwM2mVersion(Version lwM2mVersion) {
  567.             this.lwM2mVersion = lwM2mVersion;
  568.             return this;
  569.         }
  570.  
  571.         public Builder objectLinks(Link[] objectLinks) {
  572.             this.objectLinks = objectLinks;
  573.             return this;
  574.         }
  575.  
  576.         public Builder rootPath(String rootPath) {
  577.             this.rootPath = rootPath;
  578.             return this;
  579.         }
  580.  
  581.         public Builder supportedContentFormats(Set<ContentFormat> supportedContentFormats) {
  582.             this.supportedContentFormats = supportedContentFormats;
  583.             return this;
  584.         }
  585.  
  586.         public Builder supportedContentFormats(ContentFormat... supportedContentFormats) {
  587.             this.supportedContentFormats = new HashSet<>();
  588.             for (ContentFormat contentFormat : supportedContentFormats) {
  589.                 this.supportedContentFormats.add(contentFormat);
  590.             }
  591.             return this;
  592.         }
  593.  
  594.         public Builder supportedObjects(Map<Integer, String> supportedObjects) {
  595.             this.supportedObjects = supportedObjects;
  596.             return this;
  597.         }
  598.  
  599.         public Builder availableInstances(Set<LwM2mPath> availableInstances) {
  600.             this.availableInstances = availableInstances;
  601.             return this;
  602.         }
  603.  
  604.         public Builder additionalRegistrationAttributes(Map<String, String> additionalRegistrationAttributes) {
  605.             this.additionalRegistrationAttributes = additionalRegistrationAttributes;
  606.             return this;
  607.         }
  608.  
  609.         public Builder applicationData(Map<String, String> applicationData) {
  610.             this.applicationData = applicationData;
  611.             return this;
  612.         }
  613.  
  614.         private void extractDataFromObjectLinks() {
  615.             if (objectLinks != null) {
  616.                 // Define default RootPath;
  617.                 rootPath = "/";
  618.  
  619.                 // Parse object link to extract root path
  620.                 for (Link link : objectLinks) {
  621.                     if (link != null && "oma.lwm2m".equals(Link.unquote(link.getAttributes().get("rt")))) {
  622.                         rootPath = link.getUrl();
  623.                         if (!rootPath.endsWith("/")) {
  624.                             rootPath = rootPath + "/";
  625.                         }
  626.                         break;
  627.                     }
  628.                 }
  629.  
  630.                 // Extract data from link object
  631.                 supportedObjects = new HashMap<>();
  632.                 availableInstances = new HashSet<>();
  633.                 for (Link link : objectLinks) {
  634.                     if (link != null) {
  635.                         // search supported Content format in root link
  636.                         if (rootPath.equals(link.getUrl())) {
  637.                             String ctValue = link.getAttributes().get("ct");
  638.                             if (ctValue != null) {
  639.                                 supportedContentFormats = extractContentFormat(ctValue);
  640.                             }
  641.                         } else {
  642.                             LwM2mPath path = LwM2mPath.parse(link.getUrl(), rootPath);
  643.                             if (path != null) {
  644.                                 // add supported objects
  645.                                 if (path.isObject()) {
  646.                                     addSupportedObject(link, path);
  647.                                 } else if (path.isObjectInstance()) {
  648.                                     addSupportedObject(link, path);
  649.                                     availableInstances.add(path);
  650.                                 }
  651.                             }
  652.                         }
  653.                     }
  654.                 }
  655.             }
  656.         }
  657.  
  658.         private Set<ContentFormat> extractContentFormat(String ctValue) {
  659.             Set<ContentFormat> supportedContentFormats = new HashSet<>();
  660.  
  661.             // add content format from ct attributes
  662.             if (!ctValue.startsWith("\"")) {
  663.                 try {
  664.                     supportedContentFormats.add(ContentFormat.fromCode(ctValue));
  665.                 } catch (NumberFormatException e) {
  666.                     LOG.warn(
  667.                             "Invalid supported Content format for ct attributes for registration {} of client {} :  [{}] is not an Integer",
  668.                             registrationId, endpoint, ctValue);
  669.                 }
  670.             } else {
  671.                 if (!ctValue.endsWith("\"")) {
  672.                     LOG.warn("Invalid ct value [{}] attributes for registration {} of client {} : end quote is missing",
  673.                             ctValue, registrationId, endpoint);
  674.                 } else {
  675.                     String[] formats = Link.unquote(ctValue).split(" ");
  676.                     for (String codeAsString : formats) {
  677.                         try {
  678.                             ContentFormat contentformat = ContentFormat.fromCode(codeAsString);
  679.                             if (supportedContentFormats.contains(contentformat)) {
  680.                                 LOG.warn(
  681.                                         "Duplicate Content format [{}] in ct={} attributes for registration {} of client {} ",
  682.                                         codeAsString, ctValue, registrationId, endpoint);
  683.                             }
  684.                             supportedContentFormats.add(contentformat);
  685.                         } catch (NumberFormatException e) {
  686.                             LOG.warn(
  687.                                     "Invalid supported Content format in ct={} attributes for registration {} of client {}: [{}] is not an Integer",
  688.                                     ctValue, registrationId, endpoint, codeAsString);
  689.                         }
  690.                     }
  691.                 }
  692.             }
  693.  
  694.             // add mandatory content format
  695.             for (ContentFormat format : ContentFormat.knownContentFormat) {
  696.                 if (format.isMandatoryForClient(lwM2mVersion)) {
  697.                     supportedContentFormats.add(format);
  698.                 }
  699.             }
  700.             return supportedContentFormats;
  701.         }
  702.  
  703.         private void addSupportedObject(Link link, LwM2mPath path) {
  704.             // extract object id and version
  705.             int objectId = path.getObjectId();
  706.             String version = link.getAttributes().get(Attribute.OBJECT_VERSION);
  707.             // un-quote version (see https://github.com/eclipse/leshan/issues/732)
  708.             version = Link.unquote(version);
  709.             String currentVersion = supportedObjects.get(objectId);
  710.  
  711.             // store it in map
  712.             if (currentVersion == null) {
  713.                 // we never find version for this object add it
  714.                 if (version != null) {
  715.                     supportedObjects.put(objectId, version);
  716.                 } else {
  717.                     supportedObjects.put(objectId, ObjectModel.DEFAULT_VERSION);
  718.                 }
  719.             } else {
  720.                 // if version is already set, we override it only if new version is not DEFAULT_VERSION
  721.                 if (version != null && !version.equals(ObjectModel.DEFAULT_VERSION)) {
  722.                     supportedObjects.put(objectId, version);
  723.                 }
  724.             }
  725.         }
  726.  
  727.         public Registration build() {
  728.             // Define Default value
  729.             rootPath = rootPath == null ? "/" : rootPath;
  730.             lifeTimeInSec = lifeTimeInSec == null ? DEFAULT_LIFETIME_IN_SEC : lifeTimeInSec;
  731.             lwM2mVersion = lwM2mVersion == null ? Version.getDefault() : lwM2mVersion;
  732.             bindingMode = bindingMode == null ? EnumSet.of(BindingMode.U) : bindingMode;
  733.             queueMode = queueMode == null && lwM2mVersion.newerThan(Version.V1_0) ? Boolean.FALSE : queueMode;
  734.             registrationDate = registrationDate == null ? new Date() : registrationDate;
  735.             lastUpdate = lastUpdate == null ? new Date() : lastUpdate;
  736.  
  737.             // Extract data from object links if wanted
  738.             if (extractData) {
  739.                 extractDataFromObjectLinks();
  740.             }
  741.  
  742.             // Make collection immutable
  743.             // We create a new Collection and make it "unmodifiable".
  744.             if (supportedContentFormats == null || supportedContentFormats.isEmpty()) {
  745.                 supportedContentFormats = Collections.emptySet();
  746.             } else {
  747.                 supportedContentFormats = Collections.unmodifiableSet(new HashSet<>(supportedContentFormats));
  748.             }
  749.             if (supportedObjects == null || supportedObjects.isEmpty()) {
  750.                 supportedObjects = Collections.emptyMap();
  751.             } else {
  752.                 supportedObjects = Collections.unmodifiableMap(new HashMap<>(supportedObjects));
  753.             }
  754.             if (availableInstances == null || availableInstances.isEmpty()) {
  755.                 availableInstances = Collections.emptySet();
  756.             } else {
  757.                 availableInstances = Collections.unmodifiableSet(new TreeSet<>(availableInstances));
  758.             }
  759.             if (additionalRegistrationAttributes == null || additionalRegistrationAttributes.isEmpty()) {
  760.                 additionalRegistrationAttributes = Collections.emptyMap();
  761.             } else {
  762.                 additionalRegistrationAttributes = Collections
  763.                         .unmodifiableMap(new HashMap<>(additionalRegistrationAttributes));
  764.             }
  765.             if (applicationData == null || applicationData.isEmpty()) {
  766.                 applicationData = Collections.emptyMap();
  767.             } else {
  768.                 applicationData = Collections.unmodifiableMap(new HashMap<>(applicationData));
  769.             }
  770.  
  771.             // Create Registration
  772.             return new Registration(this);
  773.         }
  774.     }
  775. }
  776.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement