CoRE Working Group K. Li Internet-Draft Alibaba Group Intended status: Standards Track A. Rahman Expires: October 29, 2017 InterDigital C. Bormann, Ed. Universitaet Bremen TZI April 27, 2017 Representing Constrained RESTful Environments (CoRE) Link Format in JSON and CBOR draft-ietf-core-links-json-08 Abstract JavaScript Object Notation, JSON (RFC7159) is a text-based data format which is popular for Web based data exchange. Concise Binary Object Representation, CBOR (RFC7049) is a binary data format which has been optimized for data exchange for the Internet of Things (IoT). For many IoT scenarios, CBOR formats will be preferred since it can help decrease transmission payload sizes as well as implementation code sizes compared to other data formats. Web Linking (RFC5988) provides a way to represent links between Web resources as well as the relations expressed by them and attributes of such a link. In constrained networks, a collection of Web links can be exchanged in the CoRE link format (RFC6690). Outside of constrained environments, it may be useful to represent these collections of Web links in JSON, and similarly, inside constrained environments, in CBOR. This specification defines a common format for this. Status of This Memo This Internet-Draft is submitted in full conformance with the provisions of BCP 78 and BCP 79. Internet-Drafts are working documents of the Internet Engineering Task Force (IETF). Note that other groups may also distribute working documents as Internet-Drafts. The list of current Internet- Drafts is at http://datatracker.ietf.org/drafts/current/. Internet-Drafts are draft documents valid for a maximum of six months and may be updated, replaced, or obsoleted by other documents at any time. It is inappropriate to use Internet-Drafts as reference material or to cite them other than as "work in progress." This Internet-Draft will expire on October 29, 2017. Li, et al. Expires October 29, 2017 [Page 1] Internet-Draft Links-in-JSON April 2017 Copyright Notice Copyright (c) 2017 IETF Trust and the persons identified as the document authors. All rights reserved. This document is subject to BCP 78 and the IETF Trust's Legal Provisions Relating to IETF Documents (http://trustee.ietf.org/license-info) in effect on the date of publication of this document. Please review these documents carefully, as they describe your rights and restrictions with respect to this document. Code Components extracted from this document must include Simplified BSD License text as described in Section 4.e of the Trust Legal Provisions and are provided without warranty as described in the Simplified BSD License. Table of Contents 1. Introduction . . . . . . . . . . . . . . . . . . . . . . . . 2 1.1. Objectives . . . . . . . . . . . . . . . . . . . . . . . 3 1.2. Terminology . . . . . . . . . . . . . . . . . . . . . . . 3 2. Web Links in JSON and CBOR . . . . . . . . . . . . . . . . . 4 2.1. Background . . . . . . . . . . . . . . . . . . . . . . . 4 2.2. Information Model . . . . . . . . . . . . . . . . . . . . 4 2.3. Additional Encoding Step for CBOR . . . . . . . . . . . . 6 2.4. Converting JSON or CBOR to Link-Format . . . . . . . . . 7 2.5. Examples . . . . . . . . . . . . . . . . . . . . . . . . 8 2.5.1. Link Format to JSON Example . . . . . . . . . . . . . 8 2.5.2. Link Format to CBOR Example . . . . . . . . . . . . . 9 3. IANA Considerations . . . . . . . . . . . . . . . . . . . . . 11 3.1. Media types . . . . . . . . . . . . . . . . . . . . . . . 11 3.2. CoAP Content-Format Registration . . . . . . . . . . . . 12 4. Security Considerations . . . . . . . . . . . . . . . . . . . 13 5. References . . . . . . . . . . . . . . . . . . . . . . . . . 13 5.1. Normative References . . . . . . . . . . . . . . . . . . 13 5.2. Informative References . . . . . . . . . . . . . . . . . 13 Appendix A. Reference implementation . . . . . . . . . . . . . . 14 Acknowledgements . . . . . . . . . . . . . . . . . . . . . . . . 17 Authors' Addresses . . . . . . . . . . . . . . . . . . . . . . . 18 1. Introduction Web Linking [RFC5988] provides a way to represent links between Web resources as well as the relations expressed by them and attributes of such a link. In constrained networks, a collection of Web links can be exchanged in the CoRE link format [RFC6690] to enable resource discovery, for instance by using the CoAP protocol [RFC7252]. Li, et al. Expires October 29, 2017 [Page 2] Internet-Draft Links-in-JSON April 2017 The JavaScript Object Notation (JSON) [RFC7159] is a lightweight, text-based, language-independent data interchange format. JSON is popular in the Web development environment as it is easy for humans to read and write. The Concise Binary Object Representation (CBOR) [RFC7049] is a binary data format which requires extremely small code size, allows very compact message representation, and provides extensibility without the need for version negotiation. CBOR is especially well suited for IoT environments because of these efficiencies. When converting between a bespoke syntax such as that defined by [RFC6690] and JSON or CBOR, many small decisions have to be made. If left without guidance, it is likely that a number of slightly incompatible dialects will emerge. This specification defines a common format for representing CoRE Web Linking in JSON and CBOR. Note that there is a separate question on how to represent Web links pointing out of JSON documents, as discussed for example in [MNOT11]. While there are good reasons to stay as compatible as possible to developments in this area, the present specification is solving a different problem. 1.1. Objectives This specification has been designed based on the following objectives: o Canonical mapping * lossless conversion in both directions between any pair of [RFC6690], JSON, and CBOR ("round-tripping") * but not attempting to ensure that a sequence of conversions from one of the formats through one or both of the others and back to the original would result in a bit-wise identical representation o The simplest thing that could possibly work * Do not cater for RFC 5988 complications caused by HTTP header character set issues [RFC2047] 1.2. Terminology The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "NOT RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in Li, et al. Expires October 29, 2017 [Page 3] Internet-Draft Links-in-JSON April 2017 [RFC2119] when they appear in ALL CAPS. These words may also appear in this document in lower case as plain English words, absent their normative meanings. The term "byte" is used in its now customary sense as a synonym for "octet". CoAP: Constrained Application Protocol [RFC7252] CBOR: Concise Binary Object Representation [RFC7049] CoRE: Constrained RESTful Environments, the field of work underlying [RFC6690], [RFC7049], [RFC7252], [RFC7641], [RFC7959], and [RFC8075] IoT: Internet of Things JSON: JavaScript Object Notation [RFC7159] The objective of the JSON and CBOR mappings defined in this document is to contain information of the formats specified in [RFC5988] and [RFC6690]. This specification therefore uses the names of the ABNF productions used in those documents. 2. Web Links in JSON and CBOR 2.1. Background Web Linking [RFC5988] provides a way to represent links between Web resources as well as the relations expressed by them and attributes of such a link. In constrained networks, a collection of Web links can be exchanged in the CoRE link format [RFC6690] to enable resource discovery, for instance by using the CoAP protocol [RFC7252] and in conjunction with the CoRE resource directory [I-D.ietf-core-resource-directory]. 2.2. Information Model This section discusses the information model underlying the CORE Link Format payload. An application/link-format document is a collection of Web links ("link-value"), each of which is a collection of attributes ("link- param") applied to a "URI-Reference". We straightforwardly map: o the collection of Web links to a JSON or CBOR array of links; Li, et al. Expires October 29, 2017 [Page 4] Internet-Draft Links-in-JSON April 2017 o each link to a JSON object or CBOR map, mapping attribute names to attribute values. In the object representing a "link-value", each target attribute or other parameter ("link-param") is represented by a JSON name/value pair (member). The name is a string representation of the parameter or attribute name (as in "parmname"). The value can be a string, a boolean, or an array of strings or booleans, as described below. If the attribute value ("ptoken" or "quoted-string") is present, and a Link attribute with this name ("parmname") is present just once in the "link-value", the value is a string representation of the parameter or attribute value ("ptoken" or "quoted-string"). "quoted- string" productions are parsed (i.e, the outer quotes removed and the backslash constructions evaluated) as defined in [RFC6690] and its referenced documents, before placing them in JSON strings (in the representation of which they may gain back additional decorations such as backslashes as defined in [RFC7159]). If no attribute value ("ptoken" or "quoted-string") is present, the presence of the attribute name is indicated by using the Boolean value "true" as the value. If a Link attribute ("parmname") is present more than once in a "link-value", its values are then represented as a JSON array of JSON string values or "true"; this array becomes the value of the JSON name/value pair where the attribute name is the JSON name. Attributes occurring just once MUST NOT be represented as JSON arrays but MUST be directly represented as JSON strings or "true". (Note that [RFC6690] has cut down on the use of repeated parameter names; they are still allowed by [RFC5988] though. No attempt has been made to decode the possibly space-separated values for rt=, if=, and rel= into JSON arrays.) The URI-Reference is represented as a name/value pair with the name "href" and the URI-Reference as the value. (Rationale: This usage is consistent with the use of "href" as a query parameter for link- format query filtering and with link-format reserving the link parameter "href" specifically for this use [RFC6690]). As a non-normative summary, the resulting structure can be represented in CBOR Data Definition Language (CDDL) [I-D.greevenbosch-appsawg-cbor-cddl] as: Li, et al. Expires October 29, 2017 [Page 5] Internet-Draft Links-in-JSON April 2017 links = [* link] link = { href: tstr ; resource URI * tstr => value } value = tstr ; text value -- the normal case / true ; no value given, just the name / [2* tstr/true ] ; repeats for two or more Figure 1: CoRE Link Format Data Model 2.3. Additional Encoding Step for CBOR The above specification for JSON might have been used as is for the CBOR encoding as well. However, to further reduce message sizes, an extra encoding step is performed: "href" and some commonly occurring attribute names are encoded as small integers. The substitution is defined in Table 1: +----------+---------------+-------------------------+ | name | encoded value | origin | +----------+---------------+-------------------------+ | href | 1 | [RFC6690], [RFCthis] | | rel | 2 | [RFC5988] Section 5.3 | | anchor | 3 | [RFC5988] Section 5.2 | | rev | 4 | [RFC5988] Section 5.3 | | hreflang | 5 | [RFC5988] Section 5.4 | | media | 6 | [RFC5988] Section 5.4 | | title | 7 | [RFC5988] Section 5.4 | | type | 8 | [RFC5988] Section 5.4 | | rt | 9 | [RFC6690] Section 3.1 | | if | 10 | [RFC6690] Section 3.2 | | sz | 11 | [RFC6690] Section 3.3 | | ct | 12 | [RFC7252] Section 7.2.1 | | obs | 13 | [RFC7641] Section 6 | +----------+---------------+-------------------------+ Table 1: Integer Encoding of common attribute names This list of substitutions is fixed by the present specification; no future expansion of the list is foreseen. "href" as well as all attribute names in this list MUST be represented by their integer substitutions and MUST NOT use the attribute name in text form. *Adam's Issue number 2: What should an implementation do that receives a link-format that doesn't heed the above MUST? Is there an onus to check it?* Li, et al. Expires October 29, 2017 [Page 6] Internet-Draft Links-in-JSON April 2017 This leads to the following CDDL representation for the CBOR encoding: links = [* link] link = { href => tstr ; resource URI * label => value } href = 1 label = tstr / &( rel: 2, anchor: 3, rev: 4, hreflang: 5, media: 6, title: 7, type: 8, rt: 9, if: 10, sz: 11, ct: 12, obs: 13, ) value = tstr ; text value -- the normal case / true ; no value given, just the name / [2* tstr/true ] ; repeats for two or more Figure 2: CoRE Link Format Data Model (CBOR) 2.4. Converting JSON or CBOR to Link-Format When a JSON or CBOR representation needs to be converted back to link-format, the above process is performed in inverse. Since link- format allows serializing link parameter values both in unqouted form ("ptoken") or in quoted form ("quoted-string"), a decision has to be made for each value. Where the syntax of "ptoken" does not allow the value to be represented, the quoted form clearly needs to be used. However, when both forms are possible, the decision is arbitrary. A work-in-progress revision of [RFC5988], [I-D.nottingham-rfc5988bis], clarifies that this is indeed intended to be the case. However, existing specifications of link attributes, including those in [RFC5988] and [RFC6690], sometimes have made this decision in a specific way by only including one or the other alternative in the ABNF given for a link parameter. This requires a converter to know about all these cases, including those that have not been defined yet at the time of writing the converter. This problem becomes even harder by the fact that there is no central registry of link- attribute names. Obviously, the conversion back to link-format needs to result in a valid link-format document. The reference implementation in Appendix A has addressed this problem with the following two rules: o Where a "ptoken" representation is possible, that is used instead of "quoted-string". This rule covers most of the special cases listed above. Li, et al. Expires October 29, 2017 [Page 7] Internet-Draft Links-in-JSON April 2017 o As a special exception to the above rule, the four link attributes "anchor", "title", "rt", and "if" are always expressed as "quoted- string". This rule covers these specific four cases. This set of rules is based on the hope that future definitions of link attributes will no longer hardcode one or the other serialization. 2.5. Examples The examples in this section are based on an example on page 15 of [RFC6690] (Figure 3). ;ct=40;title="Sensor Index", ;rt="temperature-c";if="sensor", ;rt="light-lux";if="sensor", ;anchor="/sensors/temp" ;rel="describedby", ;anchor="/sensors/temp";rel="alternate" Figure 3: Example from page 15 of [RFC6690] 2.5.1. Link Format to JSON Example The link-format document in Figure 3 becomes (321 bytes, line breaks shown are not part of the minimally-sized JSON document): "[{"href":"/sensors","ct":"40","title":"Sensor Index"},{"href":"/sensors/temp","rt":"temperature- c","if":"sensor"},{"href":"/sensors/light","rt":"light- lux","if":"sensor"},{"href":"http://www.example.com/sensors/ t123","anchor":"/sensors/ temp","rel":"describedby"},{"href":"/t","anchor":"/sensors/ temp","rel":"alternate"}] " To demonstrate the handling of value-less and array-valued attributes, we extend the link-format example by examples of these (Figure 4; the "obs" attribute is defined in Section 6 of [RFC7641], while the "foo" attribute is for exposition only): ;ct=40;title="Sensor Index", ;rt="temperature-c";if="sensor";obs, ;rt="light-lux";if="sensor", ;anchor="/sensors/temp" ;rel="describedby";foo="bar";foo=3;ct=4711, ;anchor="/sensors/temp";rel="alternate" Figure 4: Example derived from page 15 of [RFC6690] Li, et al. Expires October 29, 2017 [Page 8] Internet-Draft Links-in-JSON April 2017 The link-format document in Figure 4 becomes the JSON document in Figure 5 (some spacing and indentation added): [{"href":"/sensors","ct":"40","title":"Sensor Index"}, {"href":"/sensors/temp","rt":"temperature-c","if":"sensor", "obs":true}, {"href":"/sensors/light","rt":"light-lux","if":"sensor"}, {"href":"http://www.example.com/sensors/t123", "anchor":"/sensors/temp","rel":"describedby", "foo":["bar","3"],"ct":"4711"}, {"href":"/t","anchor":"/sensors/temp","rel":"alternate"}] Figure 5: Example derived from page 15 of [RFC6690] Note that the conversion is unable to convert the string-valued "ct" attribute to a number, which would be the natural type for a Content- Format value; similarly, both "foo" values are treated as strings independently of whether they are quoted or numeric in syntax. 2.5.2. Link Format to CBOR Example This examples shows conversion from link format to CBOR format. The link-format document in Figure 3 becomes (in CBOR diagnostic format): [{1: "/sensors", 12: "40", 7: "Sensor Index"}, {1: "/sensors/temp", 9: "temperature-c", 10: "sensor"}, {1: "/sensors/light", 9: "light-lux", 10: "sensor"}, {1: "http://www.example.com/sensors/t123", 3: "/sensors/temp", 2: "describedby"}, {1: "/t", 3: "/sensors/temp", 2: "alternate"}] or, in hexadecimal (203 bytes): 85 # array(number of data items:5) a3 # map(# data item pairs:3) 01 # unsigned integer(value:1,"href") 68 # text string(8 bytes) 2f73656e736f7273 # "/sensors" 0c # unsigned integer(value:12,"ct") 62 # text(2) 3430 # "40" 07 # unsigned integer(value:7,"title") 6c # text string(12 bytes) 53656e736f7220496e646578 # "Sensor Index" a3 # map(# data item pairs:3) 01 # unsigned integer(value:1,"href") Li, et al. Expires October 29, 2017 [Page 9] Internet-Draft Links-in-JSON April 2017 6d # text string(13 bytes) 2f73656e736f72732f74 656d70 # "/sensors/temp" 09 # unsigned integer(value:9,"rt") 6d # text string(13 bytes) 74656d70657261747572 652d63 # "temperature-c" 0a # unsigned integer(value:10,"if") 66 # text string(6 bytes) 73656e736f72 # "sensor" a3 # map(# data item pairs:3) 01 # unsigned integer(value:1,"href") 6e # text string(14 bytes) 2f73656e736f72732f6c 69676874 # "/sensors/light" 09 # unsigned integer(value:9,"rt") 69 # text string(9 bytes) 6c696768742d6c7578 # "light-lux" 0a # unsigned integer(value:10,"if") 66 # text string(6 bytes) 73656e736f72 # "sensor" a3 # map(# data item pairs:3) 01 # unsigned integer(value:1,"href") 78 23 # text string(35 bytes) 687474703a2f2f777777 2e6578616d706c652e63 6f6d2f73656e736f7273 2f74313233 # "http://www.example.com/sensors/t123" 03 # unsigned integer(value:3,"anchor") 6d # text string(13 bytes) 2f73656e736f72732f74 656d70 # "/sensors/temp" 02 # unsigned integer(value:2,"rel") 6b # text string(11 bytes) 6465736372696265646279 # "describedby" a3 # map(# data item pairs:3) 01 # unsigned integer(value:1,"href") 62 # text string(12 bytes) 2f74 # "/t" 03 # unsigned integer(value:3,"anchor") 6d # text string(13 bytes) 2f73656e736f72732f74 656d70 # "/sensors/temp" 02 # unsigned integer(value:2,"rel") 69 # text string(9 bytes) 616c7465726e617465 # "alternate" Figure 6: Web Links Encoded in CBOR Li, et al. Expires October 29, 2017 [Page 10] Internet-Draft Links-in-JSON April 2017 3. IANA Considerations 3.1. Media types This specification registers the following additional Internet Media Types: Type name: application Subtype name: link-format+json Required parameters: None Optional parameters: None Encoding considerations: Resources that use the "application/link- format+json" media type are required to conform to the "application/json" Media Type and are therefore subject to the same encoding considerations specified in [RFC7159], Section 11. Security considerations: See Section 4 of [RFCthis]. Published specification: [RFCthis]. Applications that use this media type: Applications that interchange collections of Web links based on CoRE link format [RFC6690] in JSON. Additional information: Magic number(s): N/A File extension(s): N/A Macintosh file type code(s): TEXT Person & email address to contact for further information: Carsten Bormann Intended usage: COMMON Change controller: IESG and Type name: application Subtype name: link-format+cbor Li, et al. Expires October 29, 2017 [Page 11] Internet-Draft Links-in-JSON April 2017 Required parameters: None Optional parameters: None Encoding considerations: Resources that use the "application/link- format+cbor" media type are required to conform to the "application/cbor" Media Type and are therefore subject to the same encoding considerations specified in [RFC7049], Section 7. Security considerations: See Section 4 of [RFCthis]. Published specification: [RFCthis]. Applications that use this media type: Applications that interchange collections of Web links based on CoRE link format [RFC6690] in CBOR. Additional information: Magic number(s): N/A File extension(s): N/A Macintosh file type code(s): CBOR Person & email address to contact for further information: Kepeng Li Intended usage: COMMON Change controller: IESG 3.2. CoAP Content-Format Registration IANA is requested to assign CoAP Content-Format IDs for the above media types in the "CoAP Content-Formats" sub-registry, within the "CoRE Parameters" registry [RFC7252]. All IDs are assigned from the "Expert Review" (0-255) range. The assigned IDs are show in Table 2. +------------------------------+-------+ | Media type | ID | +------------------------------+-------+ | application/link-format+cbor | TBD64 | | application/link-format+json | TBD54 | +------------------------------+-------+ Table 2: CoAP Content-Format IDs Li, et al. Expires October 29, 2017 [Page 12] Internet-Draft Links-in-JSON April 2017 4. Security Considerations The security considerations relevant to the data model of [RFC6690], as well as those of [RFC7049] and [RFC7159] apply. 5. References 5.1. Normative References [RFC2119] Bradner, S., "Key words for use in RFCs to Indicate Requirement Levels", BCP 14, RFC 2119, DOI 10.17487/RFC2119, March 1997, . [RFC5988] Nottingham, M., "Web Linking", RFC 5988, DOI 10.17487/RFC5988, October 2010, . [RFC6690] Shelby, Z., "Constrained RESTful Environments (CoRE) Link Format", RFC 6690, DOI 10.17487/RFC6690, August 2012, . [RFC7049] Bormann, C. and P. Hoffman, "Concise Binary Object Representation (CBOR)", RFC 7049, DOI 10.17487/RFC7049, October 2013, . [RFC7159] Bray, T., Ed., "The JavaScript Object Notation (JSON) Data Interchange Format", RFC 7159, DOI 10.17487/RFC7159, March 2014, . 5.2. Informative References [I-D.greevenbosch-appsawg-cbor-cddl] Birkholz, H., Vigano, C., and C. Bormann, "CBOR data definition language (CDDL): a notational convention to express CBOR data structures", draft-greevenbosch-appsawg- cbor-cddl-10 (work in progress), March 2017. [I-D.ietf-core-resource-directory] Shelby, Z., Koster, M., Bormann, C., and P. Stok, "CoRE Resource Directory", draft-ietf-core-resource-directory-10 (work in progress), March 2017. [I-D.nottingham-rfc5988bis] Nottingham, M., "Web Linking", draft-nottingham- rfc5988bis-05 (work in progress), April 2017. Li, et al. Expires October 29, 2017 [Page 13] Internet-Draft Links-in-JSON April 2017 [MNOT11] Nottingham, M., "Linking in JSON", November 2011, . [RFC2047] Moore, K., "MIME (Multipurpose Internet Mail Extensions) Part Three: Message Header Extensions for Non-ASCII Text", RFC 2047, DOI 10.17487/RFC2047, November 1996, . [RFC7252] Shelby, Z., Hartke, K., and C. Bormann, "The Constrained Application Protocol (CoAP)", RFC 7252, DOI 10.17487/RFC7252, June 2014, . [RFC7641] Hartke, K., "Observing Resources in the Constrained Application Protocol (CoAP)", RFC 7641, DOI 10.17487/RFC7641, September 2015, . [RFC7959] Bormann, C. and Z. Shelby, Ed., "Block-Wise Transfers in the Constrained Application Protocol (CoAP)", RFC 7959, DOI 10.17487/RFC7959, August 2016, . [RFC8075] Castellani, A., Loreto, S., Rahman, A., Fossati, T., and E. Dijk, "Guidelines for Mapping Implementations: HTTP to the Constrained Application Protocol (CoAP)", RFC 8075, DOI 10.17487/RFC8075, February 2017, . [RUBY] "Information technology -- Programming languages -- Ruby", ISO/IEC 30170:2012, April 2012. Appendix A. Reference implementation A reference implementation of a converter from [RFC6690] link-format to JSON and CBOR (and back to link-format) in the programming language Ruby [RUBY] is reproduced below. # require 'strscan' require 'json' require 'cbor-pretty' class String def as_utf8 force_encoding(Encoding::UTF_8) end end Li, et al. Expires October 29, 2017 [Page 14] Internet-Draft Links-in-JSON April 2017 module CoRE module Links def self.map_to_true(a) Hash[a.map{ |t| [t, true]}] end PTOKENCHAR = %r"[\[\]\w!#-+\--/:<-?^-`{-~@]" QUOSTRCHAR = %r{(?:[^"\\]|\\.)} # to be used inside " ATTRCHAR = %r"[\w!#$&+.^`|~-]" MUSTBEQUOTED = map_to_true(%w{anchor title rt if}) ANCHORNAME = "href" SCANATTR = %r{(#{ATTRCHAR}+)(?:=(?:(#{PTOKENCHAR}+)|"(#{QUOSTRCHAR}*)"))?} # " RAWMAPPINGS = <<-DATA href: 1, rel: 2, anchor: 3, rev: 4, hreflang: 5, media: 6, title: 7, type: 8, rt: 9, if: 10, sz: 11, ct: 12, obs: 13, DATA MAPPINGS = Hash.new {|h, k| k} RAWMAPPINGS.scan(/([-\w]+)\s*:\s*([-\w]+),/) do |n, v| MAPPINGS[n] = Integer(v) end def self.parse(*args) WLNK.parse(*args) end class WLNK attr_accessor :resources def initialize(r = []) # make sure the keys are strings @resources = r.to_ary # make sure it's an Array end def self.parse(s, robust = true) wl = WLNK.new ss = StringScanner.new(s.as_utf8) ss.skip(/\s+/) if robust while ss.scan(%r{<([^>]+)>}) res = { ANCHORNAME => ss[1].as_utf8 } ss.skip(/\s*/) if robust while ss.skip(/;/) ss.skip(/\s*/) if robust unless ss.scan(SCANATTR) raise ArgumentError, "must have attribute behind ';' Li, et al. Expires October 29, 2017 [Page 15] Internet-Draft Links-in-JSON April 2017 at: #{ss.peek(20).inspect} (byte #{ss.pos})" end key = ss[1].as_utf8 value = ss[2] || (ss[3] ? ss[3].gsub(/\\(.)/) { $1 } : true) if res[key] res[key] = Array(res[key]) << value else res[key] = value end ss.skip(/\s*/) if robust end wl.resources << res break unless ss.skip(/,/) ss.skip(/\s*/) if robust end ss.skip(/\s*/) if robust raise ArgumentError, "link-format unparseable at: #{ss.peek(20).inspect} (byte #{ss.pos})" unless ss.eos? wl end def to_json JSON.pretty_generate(@resources) end def to_cbor CBOR.encode(@resources.map {|r| Hash[r.map { |k, v| [MAPPINGS[k], v] }]}) end def to_wlnk resources.map do |res| res = res.dup u = res.delete(ANCHORNAME) ["<#{u}>", *res.map do |k, v| if String === v if MUSTBEQUOTED[k] || v !~ /\A#{PTOKENCHAR}+\z/ "#{k}=\"#{v.gsub(/[\\"]/) { |x| "\\#{x}"}}\"" else "#{k}=#{v}" end else "#{k}" end end].join(';') end.join(",") end end end end Li, et al. Expires October 29, 2017 [Page 16] Internet-Draft Links-in-JSON April 2017 lf = CoRE::Links.parse(ARGF.read) puts lf.to_json # JSON puts CBOR.pretty(lf.to_cbor) # CBOR "pretty" binary form puts lf.to_wlnk # RFC 6690 link-format # Acknowledgements Special thanks to Bert Greevenbosch who was an author on the initial version of a contributing document as well as the original author on the CDDL notation. Hannes Tschofenig made many helpful suggestions for improving this document. Li, et al. Expires October 29, 2017 [Page 17] Internet-Draft Links-in-JSON April 2017 Authors' Addresses Kepeng LI Alibaba Group Wenyixi Road, Yuhang District Hangzhou, Zhejiang 311121 China Email: kepeng.lkp@alibaba-inc.com Akbar Rahman InterDigital Communications, LLC 1000 Sherbrooke Street West Montreal, Quebec H3A 3G4 Canada Phone: +1-514-585-0761 Email: akbar.rahman@interdigital.com Carsten Bormann (editor) Universitaet Bremen TZI Postfach 330440 Bremen D-28359 Germany Phone: +49-421-218-63921 Email: cabo@tzi.org Li, et al. Expires October 29, 2017 [Page 18]