home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 35 Internet / 35-Internet.zip / srev13g.zip / negotiat.doc < prev    next >
Text File  |  1999-06-26  |  27KB  |  684 lines

  1. 24 June 1999
  2.              SRE-http and Content Negotiation
  3.  
  4. 1) Introduction
  5.  
  6. Content negotiation refers to the choosing of a best representation
  7. of a web resource from several alternatives.
  8.  
  9. In general, content negotiation is  used to choose between resources
  10. created with one of several languages, or one of several mimetypes. 
  11. Content negotiation can also be used to choose between resources
  12. using alternate character sets, and to choose shorter documents.  
  13. In the future, content negotiation may also be used to choose documents 
  14. using certain features (such as documents using different versions of html). 
  15.  
  16. There are basically two forms of content negotiation:
  17.  
  18.   1)Server-side. 
  19.      Server-side content negotiation (which is defined in http/1.0) 
  20.      is performed by the server -- the server uses ACCEPT request
  21.      headers (provided by the client) to automatically choose 
  22.      and return one of serveral variants.
  23.  
  24.   2)Client-side. 
  25.       Client-side content negotiation (which is new to http/1.1) 
  26.       is accomplished by the client automatically requesting one of 
  27.       several variants:
  28.          the choice is based on a "variants list", containing
  29.          URL's and descriptive information, contained in 
  30.          response headers returned by the server.
  31.  
  32. SRE-http supports both server-side  and client-side content negotiation.               
  33.  
  34.                          ---------------------
  35.   
  36. II) Specifying a negotiable resource
  37.  
  38. To specify a "negotiable" resource (a web resource with several possible
  39. variants) requires 3 steps:
  40.   
  41.   1) Create several "variants" of a resource
  42.   2) Create a file, in your web-space, containing a "variant list"
  43.   3) Create a special !NEGOTIATE alias pointing to this file
  44.  
  45. These steps are described in the next three sections.
  46.  
  47. Notes:
  48.  
  49.   * SRE-http's implementation of content negotiation is loosely based on
  50.     Apache 1.3. You might want to examine 
  51.         http://www.apache.org/docs/content-negotiation.html
  52.     for a different description.
  53.  
  54.   * For a technical discussion of content-negotiation, see RFC 2295
  55.     "Transparent Content Negotiation in HTTP" at:
  56.     http://gewis.win.tue.nl/~koen/conneg/
  57.  
  58.   * The rationale for client-side content negotiation is that the browser
  59.     is best equipped to choose a variant (given descriptive information
  60.     on the variants mimetype, language, etc.)  Furthermore, it is thought that
  61.     it is wasteful of bandwith to provide the full range of Accept: headers 
  62.     on every request (since most resources will not be subject to content
  63.     negotiation). One the other hand, client-side negotiation does require
  64.     two requests...
  65.  
  66.   * Note that SRE-http does NOT completely implement "transparent content 
  67.     negotiation" protocol. In particular, some of the required (variant
  68.     specific) http/1.1 caching is not attempted.
  69.  
  70.                      -------------------------
  71.  
  72. II.1) Creating variants
  73.  
  74. Basically, a variant is any server resource. This includes documents, images, 
  75. and even cgi-bin scripts and sre-http addons.  The notion is that variants 
  76. all represent variations of the same information.  For example,
  77. you may have several translations of the same document (say, an English, 
  78. Finnish and Korean version) which you'ld like to  automatically send
  79. to the appropropriate clients.
  80.  
  81. There are a few constraints:
  82.   1) variants must be on the same server as the "variant list" (discussed next).
  83.      It is considered good practice (from a security standpoint) for 
  84.      each variant to be in the same directory as the variant list. 
  85.   2) variants must be retrievable via GET requests.  That is, each
  86.      variant should be accessible with a standard URL; which also means that 
  87.      content negotiation will NOT work with POST requests.
  88.  
  89.                      -------------------------
  90.  
  91. II.2) Creating a Variant List
  92.  
  93. The variant list is at the heart of SRE-http's implementation of content
  94. negotiation. The variant list is a simple (text) file containing
  95. several multi-line records. This file should be accessible from the web.
  96. That is: it must be placed in (or under) the GoServe data directory, or in a 
  97. virtual directory. 
  98.  
  99. Each record in the variant lists must specify a URI (a selector),
  100. and several pieces of identifying information.  This information
  101. is used to specify up to five "dimensions of negotiation": mimetype,
  102. charset, language, encoding, and length.
  103.  
  104. The syntax of these multi-line records is (note that a wildcarded form
  105. of these records can also be specified, as discussed in section II.4 below):
  106.  
  107. URI: a_selector
  108. Content-type: type/subtype ; charset=a_charset ; qs=m.mm
  109. Content-language: l1, l2 
  110. Content-encoding: enctype
  111. Content-length: nnnn
  112.  
  113. Where:
  114.  
  115.   URI is required.
  116.  
  117.     URI should be a valid selector; that is, site information can not be 
  118.     included -- the resource must be on  the same site as the variant list.
  119.     Note that relative URI's are interepreted relative to the location 
  120.     of the  "variant list"
  121.  
  122.   Content-type: Content-type is required. It contains 3 sub-fields.
  123.  
  124.      type/subtype: Only the type/subtype subfield is required.
  125.                    It identifies the mime-type of this variant.
  126.  
  127.      charset: Optional. Identifies the character set. If not specified,
  128.               a ISO-8859-1 (latin1) is assumed
  129.  
  130.      qs: Optional. The "selection quality". Must be between 0.0 and 1.0.
  131.          0.0 means "unacceptable", 1.0 means "perfect representation".
  132.          If not specified, a value of 1.0 is assumed.  All else equal,
  133.          variants with higher values are preferentially chosen. Note that
  134.          qs is used, while "q" is used in accept headers.
  135.  
  136.   Content-language: Optional.
  137.  
  138.      A comma delimited list of 2  character languages codes 
  139.      (i.e.; EN for  English, FR for French, DE for German). 
  140.      Note that the 2-2 letter codes, such as En-US, are
  141.      shortened (only the first two characters are used).
  142.  
  143.   Content-encoding: Optional.
  144.  
  145.      A comma delimited list of content encoding types (i.e.; identity,
  146.      gzip, and compress).
  147.  
  148.   Content-length: Optional.
  149.  
  150.      The length of the resource.  If not specified, a length of 0 is
  151.      assumed. Note that "longer" resources are less likely to be chosen
  152.      (all else equal).
  153.  
  154.   Description: Optional
  155.       An optional description of this variant.
  156.  
  157.   Features: Optional
  158.       Features allows you to note special "features" of the variant.
  159.       Although not widely supported, in the future browsers may use
  160.       such information to choose a variant (SRE-http does NOT use features
  161.       in it's variant selection algorithim).
  162.       For details on the structure of the feature, please see RFC2295.
  163.  
  164. Notes:
  165.   *  Appendix A contains an example of a variant list file.
  166.   *  When a variant is selected, it's Content-Type, Content-Language,
  167.      and Content-Encoding are returned as response headers. Thus,
  168.      in most cases the Content-Type specified in a variant list will 
  169.      override the "default" Content-Type (i.e.; the mimetype derived from 
  170.      the file's extension). The exception to this rule is when
  171.      the variant is a CGI script or an SRE-http addon, in which
  172.      case this information is ignored.
  173.  
  174.  
  175.                      -------------------------
  176.  
  177. II.3) Identifying a negotiable resource.
  178.  
  179. SRE-http uses a special "alias" to identify variant lists.  That is,
  180. unless explicitily identified as a variant list, a request for a variant
  181. list will be treated in the normal fashion-- i.e.; the file would be
  182. returned verbatim (say, as a text document).
  183.  
  184. To identify a variant list, you must add special lines to your ALIASES
  185. file. This can be done with the configurator, or by hand.
  186.  
  187. Note that there are two forms of this special alias -- a simple form
  188. and a wildcard form:
  189.  
  190. a) Simple form:
  191.  
  192.   The syntax of the "simple" form is:
  193.       a_selector !NEGOTIATE
  194.  
  195.   where a_selector is a selector pointing to the variant list.
  196.  
  197.   For example:
  198.      /VARTEST/VAR1.LST !NEGOTIATE
  199.   could mean: "VAR1.LST file in the VARTEST subdirectory of the GoServe
  200.               data directory is a variant list"
  201.  
  202.   Note that, unlike most SRE-http aliases, there is no explicit
  203.   "replacement". Actually, you can think of the variant list itself
  204.   as an extension of SRE-http's aliasing -- it contains instructions used 
  205.   to decide which (of several) replacements to use.
  206.  
  207. b) Wildcarded form
  208.   
  209.    The syntax of the wildcarded form is:
  210.         wild_sel !NEGOTIATE  variant_sel
  211.    where
  212.         wild_sel is a * (wildcard) containing "target"
  213.         variant_sel is a valid selector that points to a variant list
  214.    
  215.    For example:
  216.         /MANUALS/*.HTM !NEGOTIATE /MANUALS/DOCS.LST
  217.  
  218.    In this case, all request selectors that match MANUALS/* (note that the
  219.    leading / is ignored) will use the variant list specified in 
  220.    /MANUALS/DOCS.LST.  Please see the next section for details on how 
  221.    variants are resolved when this wild_sel form is used.
  222.  
  223. Once you've accomplished these steps, all you need to do is put a URL
  224. pointing to "a_selector" (or that will alias-match "wild_sel"), and hope 
  225. that your client's browser either provides useful ACCEPT headers, or knows how 
  226. to do client side content negotiation.
  227.  
  228.                      -------------------------
  229.  
  230.  
  231. II.4 Wildcarded variants
  232.  
  233. As outlined above, one must create a unique variant list (and a unique
  234. alias) for all negotiable resources. This may become quite tedious,
  235. especially when you have multiple sets of documents. For example, if you
  236. have a 10 chapter manual in 3 languages (hence, 30 files), it could be
  237. advantageous (that is, a lot less trouble) to use some wildcarded "variant 
  238. list" for all 10 chapters.
  239.  
  240. In recognition of this possibility, SRE-http supports a special form of 
  241. variant list (and ALIAS) that supports such "multiple sets of negotiable
  242. resources".  The specification of these sets requires two changes to
  243. the simple case. 
  244.  
  245. The first difference is discussed above -- the use of the "wildcarded form" 
  246. of an alias.  The second involves modifications to the variant list file.
  247.  
  248. Recollect that the wildcarded form directs many possible "request selectors"
  249. to a single variant list.  Thus, the variant list must contain information that
  250. allows the request selector to influence the value of the URI: field of each
  251. record in the variant list.  To do this, two steps are required.
  252.  
  253.    a) A 
  254.        PATTERN: wild_sel 
  255.     entry should be put at the top of the variant list.
  256.     For example:
  257.         Pattern: /manuals/*.HTM  --    (note that a leading / is ignored)
  258.  
  259.       **  The value of "wild_sel" used in a PATTERN: entry should be the same 
  260.           as the "wild_sel" used as the "target" portion of the wildcarded alias 
  261.           (that is used to identify the variant list).
  262.  
  263.    b) The URI: fields may contain *s. 
  264.       As with other features, SRE-http will replace these * (in the URI: 
  265.       entriess) with corresponding portions in the request selector.
  266.  
  267.       For example:
  268.         i) if the request selector is: manual/chap1.htm
  269.        ii) the alias is:  manual/*  !negotiate  manual/docs.lst
  270.       iii) manual/docs.lst contains
  271.  
  272.                pattern: manual/*
  273.                 
  274.                URI: de/*
  275.                Content-type: text/html
  276.                Content-Language: de
  277.  
  278.                Uri: en/*
  279.                Content-type: text/html
  280.                Content-language: en
  281.  
  282.       iv) If the request contain an accept-language: en request header, then
  283.               en/chap1.htm would be used
  284.          
  285.           If the request contain an accept-language: de request header, then
  286.               de/chap1.htm would be used
  287.  
  288.           That is, the * in the Pattern: (in manual/*) "corresponds to" 
  289.           chap1.htm, which is then used as a substitute for the * in the various 
  290.           various URI: entries.
  291.  
  292.                      -------------------------
  293.  
  294. III. The content negotiation algorithim.
  295.  
  296. The following sketches the algorithim used by SRE-http. Note that this
  297. is used both for "server side negotiation" (when the client does not
  298. include a Negotiate: request header), and as a "remove variant selection
  299. algorithim" (when the client includes a Negotiate: * request header).
  300.  
  301.  
  302. 1) First, SRE-http checks for a "Negotiate:" request header. If no 
  303.    such header exists, then server-side negotiation is always
  304.    attempted. If this header does exist, then server-side negotiation
  305.    may be attempted (see the notes for details).
  306.  
  307. 2) If server-side negotiation is to be attempted, by default
  308.    the following selection algorithim is used.  
  309.  
  310.       If the client allows  a "remote variant selection algorithim"
  311.       (by including a Negotiate: n.n request header), then a custom
  312.       procedure can be used instead (see Appendix B for the details).
  313.  
  314.    Note that this is a "leave as soon as a definitive answer is found"
  315.    method -- latter steps are only used if earlier steps yield ties.
  316.    Furthermore, variants eliminated in earlier steps are NOT 
  317.    available -- they are NOT considered in latter steps.
  318.    Lastly, if all variants are eliminated, a suitable "could not find
  319.    representation" response is immediately returned.
  320.  
  321.    a) Accept: headers are read. Accept: headers contains information
  322.       on acceptable mime-types.  This information can contain "selection
  323.       quality" (q) information.  
  324.       The variant with the best "combined" quality is used.  Combined quality
  325.       is deterimined by multiplying the variant-list q(uality) by the accept: header
  326.       "q: factors. 
  327.       If there are ties (i.e.; several mimetypes have a combined q of 1.0),
  328.       then move to step b. If there is no accept: header (most browsers
  329.       send some form of Accept: header) then skip this step.
  330.  
  331.    b) Accept-language: headers are read. These headers can also contain
  332.       "language specific q modifiers".  The variant (of those surviving
  333.       step a) with the highest language "q" factor is used. 
  334.       If there are ties, move to step c. If there is no accept-language
  335.       header, this step is skipped. Note that the content-language entries
  336.       in the variant list should NOT include "q" factors.
  337.  
  338.  
  339.    c) Accept-Encoding: headers are read. These headers can also contain
  340.       "encoding specific q modifiers".  The variant (of those surviving
  341.       step b) with the highest encoding "q" factor is used. 
  342.       If there are ties, move to step d. If there is no accept-encoding
  343.       header, this step is skipped. Note that the content-encoding entries
  344.       in the variant list should NOT include "q" factors.
  345.  
  346.    d) A accept-charset: header is read. Variants that do not match this
  347.       charset are dropped.
  348.       If there are ties then move to step e. If there is no accept-charset
  349.       header then skip this step.
  350.  
  351.    e) Use the variant with the smallest content-length (as pulled from the 
  352.       variant list).
  353.       If there are ties, move to step f.
  354.  
  355.    f) Use the first of the remaining variants.
  356.  
  357. 3) If client-side negotiation is to be used, SRE-http returns a special
  358.    "300" return  code. The body of the response contains an <UL> list 
  359.    containing links to each  variant. Furthermore, the variant list 
  360.    (suitably formatted) is returned in an Alternates: response header.
  361.  
  362.  
  363. Note:
  364.  
  365.    * SRE-http recognizes several values in the Negotiate: header (any
  366.      combination of them can appear in a comma delimited list)
  367.  
  368.         trans:  client supports client side content negotiation
  369.         vlist:  always send Alternates: response header (implies trans)
  370.             *:  server should attempt to choose best variant (implies trans).
  371.       guess-small: always send Alternates: response header (implies trans)
  372.                    This is minimal support -- with full support, sometimes
  373.                    a sufficiently small "best variant" guess is returned.
  374.         n.n     : A decimal number, such as 4.2.
  375.                  This specifies the major and minor versions of a customized
  376.                  "remote variant selection algorithim" (RVSA) -- a custom
  377.                  procedure to replace SRE-https built in variant selection
  378.                  algorithim. See APPENDIX B for details on how to
  379.                  add a procedure to implement your favorite RVSA!
  380.  
  381.      In the following cases, server-side negotiation is not attempted:
  382.  
  383.         Negotiate: trans
  384.         Negotiate: vlist
  385.         Negotiate: vlist,trans   
  386.         Negotiate: guess-small
  387.  
  388.      In these cases,SRE-http returns a "300 Multiple Choices" response.
  389.  
  390.      This response always includes an Alternates: header (containing a suitably
  391.      formatted version of the variant list). In addition, a <UL> list
  392.      of links to each variant is returned in the body of the response.
  393.          The assumption is that (in most cases) the user-agent 
  394.          (the browser) will use the variant list to choose  a best 
  395.          variant; but if it can't, the list will be displayed and the 
  396.          human can manually choose.
  397.  
  398.      When * is included, then server-side content negotiation will be
  399.      attempted. In particular:
  400.          Negotiate: *, vlist
  401.      means "attempt to find best match, but always return the variant list"
  402.      In contrast
  403.          Negotiate: *
  404.      means "return the best match, only return a variant list if no best
  405.      match found".
  406.  
  407.      When a "n.n" RVSA token is included, and the appropriate procedure
  408.      has been defined, then SRE-http will server-side content negotation
  409.      will be attempted.  See Appendix B for the details.
  410.  
  411.      In either case (that is, whenever * or an n.n  appears in the 
  412.      Negotiate: header), failing to find a best match causes a  
  413.      "406 No acceptable representation"  response to be returned. 
  414.      This 406 response is similar to the 300 response described above -- 
  415.      it contains an Alternates: header and  a <UL> list of links.
  416.  
  417.  * To repeat: if no Negotiate: request header exists, then server-side
  418.    content negotiation is attempted. If no best-match can be found, then
  419.    a 404 response, containing a <UL> list of links to each variant,
  420.    is returned (but no Alternates: header).
  421.  
  422.  * Whenever server-side negotiation (either pure server side, or
  423.    due to a Negotiate:* header) is succesful, a Vary: header
  424.    will be included (Vary headers are used by proxy servers)
  425.  
  426.  * When a quality value is not specified (either as q factor in the 
  427.    Content-type field in the variant list, or as a "q" factor in an Accept: 
  428.    or Accept-Language request header), a value of 1.0 is assumed. 
  429.    There are a few exceptions:
  430.        i)if a */* or xxx/* appear (in the Accept: header), and if no other
  431.          mimetypes have a q modifier, then */* is assigned a value of 0.01,
  432.          and xxx/* is given a value of 0.02.
  433.       ii)records in the variant list with no content-language field are given
  434.          a language quality factor of 0.01.
  435.    Both these exceptions are tricks that cause these "defaults" to be used
  436.    when no better match exists.
  437.  
  438.  * You can specify multiple languages in the Content-language entry
  439.    (in a variant list record). However, you can NOT specify a "q" modifier
  440.    for these languages.  Note that the accept-language header MAY contain
  441.    several languages, each of which may have a "q" modifier.
  442.  
  443.  * If no charset is specified (in a variant list record), then 
  444.    ISO-8859-1 (latin1) is assumed.
  445.  
  446.  * If no content-length is specified (in a variant list record), then 
  447.    a length of 0 is assumed. That is, content-length is really a final
  448.    "quality check", with lower values (and unspecified values) preferred.
  449.  
  450.  * Hint: the Options-General-Language tab of Netscape can be used to 
  451.    automatically generate Accept-language headers.
  452.  
  453.  * WARNING: the variant returned by server side negotiation should NEVER
  454.             be a negotiable resource. If this should happen, SRE-http
  455.             will return a 506 response (Variant Also Negotiates).
  456.  
  457.                      -------------------------
  458.    
  459.  
  460. Appendix A) Sample Variants file.
  461.  
  462.  
  463.         ---------------------- Start example -----------
  464. ; this is sample variant file
  465.  
  466. URI: foo
  467.  
  468. Uri:foo.fr.de.html
  469. content-type: text/html 
  470. content-language: sp,fr-ca,de
  471. content-length: 2005
  472.  
  473. Uri:foo.txt
  474. content-type: text/plain ; q=0.5
  475. content-length: 2005
  476. content-language: en 
  477. description: this is the english text version
  478.  
  479. Uri:foo.gz
  480. content-type: text/plain ; q=0.5
  481. content-length: 2005
  482. content-encoding: gzip
  483. content-language: en 
  484.  
  485. uri: /status?
  486. content-type: application/octet-stream
  487.  
  488. uri: foo.en.html
  489. content-type: text/html ; charset=iso-8859-1 ; q=1
  490. content-language: en
  491. features: tables frames
  492.  
  493. uri:foo.default
  494.  
  495.  
  496.         ---------------------- End of example -----------
  497.  
  498. Notes:
  499.   * Lines beginning with ; are comments, and are ignored
  500.  
  501.   * Each, typically multi-line record, contains a
  502.         URI:, and optionally any combination of content-type, 
  503.         content-languate, and content-length
  504.  
  505.   * Blank lines are treated as "record delimiters"
  506.  
  507.   * The first "one line record" URI: entry is optional -- it's skipped
  508.  
  509.   * Note that content-encoding and content-features are NOT supported
  510.  
  511.   * Content-length is the estimated size of the file, 
  512.     it does NOT have to be the actual size of the file.
  513.     All else equal, smaller "lengths" are preferentially returned.  
  514.  
  515.   * Content-language is a comma delimited set of languages 
  516.  
  517.   * Content-encoding is an encoding type, with "identity" meaning
  518.     "no encoding". Only one encoding-type can be specified.
  519.  
  520.   * Content-type contains 3 fields. The type/subtype field is required,
  521.     the charset= field is optional (iso-8859-1 is the default), and q
  522.     is the (optional) "quality" measure used to weight the variants.
  523.  
  524.   * Note the last entry is a "fall back" variant (the client's user-agent
  525.     can choose this if all else fails).
  526.  
  527.  
  528.                      -------------------------
  529.  
  530.  
  531. Appendix B: Specifying a Remote Variant Selection Algorithim
  532.  
  533. SRE-http provides a simple hook by which a custom remote variant
  534. selection algorithims (RVSA) can be implemented.  The process is:
  535.  
  536. a) obtain the RVSA. 
  537.  
  538. b) write a rexx procedure that calls this rvsa
  539.  
  540. c) save this procedure into macrospace using a name of
  541.    SREF_RVSA_n, where "n" is the major version number
  542.    of the rvsa.
  543.  
  544.    For example, if the request contains:
  545.        Negotiate: 2.3,vlist
  546.    then SREF_RVSA_2 is appropriate "macrospace" procedure name.
  547.  
  548. In the simplest case, the rvsa procedure will be a rexx procedure;
  549. in which step a and b are combined.
  550.  
  551. The rvsa procedure (say, SREF_RVSA_2) will be called with
  552. two arguments, the version number, and the list of alternates.
  553. For example, to read these arguments the procedure could use:
  554.   parse arg version,altlist
  555.  
  556. In the above example (Negotiate: 2.3,vlist) the version number would 
  557. be "2.3" (without the quotes). The list of alternates is simply a 
  558. copy of the Alternates: header (that would be returned to the client).
  559.  
  560. The rvsa procedure should use this information, along with request
  561. specific information (such as the various Accept headers, which 
  562. can be read using the GoServe reqfield function) to determine which
  563. variant is best.   The number of this best variant should be
  564. returned; or a 0 should be returned if there is no best match.
  565.  
  566. For example, if the second variant (in the list of alternates) is
  567. best, then SREF_RVSA_2 should return a "2" (without the quotes).
  568.  
  569. Notes:
  570.  
  571.   * You can use RXU, REXXLIB, or other DLLs to create macrospace
  572.     procedures
  573.  
  574.   * For details on the structure of the alternates list, see RFC2295.
  575.     (see Appendix 3 for an example).
  576.  
  577.                      -------------------------
  578.  
  579.  
  580. Appendix C: Example of a TCN Request and Response
  581.  
  582.  
  583. The following is a simple example of TCN request, and the response
  584. from SRE-http.
  585.  
  586. Assuming that:
  587.   TSTHTM/TSTHTM.NEG
  588. is a negotiable resource, and TSTHTM.NEG has the following structure:
  589.  
  590.    ;---- TSTHTM.NEG is a negotiable resources
  591.    uri:tsthtm
  592.  
  593.    uri:tst.1
  594.    content-type: text/plain; qs=0.8
  595.    content-language: en 
  596.  
  597.    uri: tst.2
  598.    content-type: text/plain ; qs=0.3
  599.    content-language: fr 
  600.    description: The French Version
  601.    features: tables [abc def] 
  602.  
  603.    uri: /gene_test?
  604.    content-type: application/octet-stream; charset=cyrillic
  605.    content-language: ru
  606.    ;---- End of TSTHTM.NEG
  607.  
  608.  
  609. The urI:
  610.   http://foo.bar.net/tsthtm/tsthtm.neg
  611.  
  612. which yields the request:
  613.  
  614.  
  615.    GET /tsthtm/tsthtm.neg  HTTP/1.1
  616.    HOST:foo.bar.net
  617.    Negotiate: vlist,*
  618.    Accept: text/plain
  619.    Accept-language: fr
  620.  
  621. would yield the response:
  622.  
  623.   HTTP/1.1 200 Ok
  624.   Date: Sat, 26 Jun 1999 13:49:10 GMT
  625.   Accept-Ranges: bytes
  626.   Connection: close
  627.   Last-Modified: Thu, 24 Jun 1999 05:52:38 GMT
  628.   ETag: "990624015238_18;7964E38D"
  629.   Server: GoServe for OS/2, version 2.52; SRE-http 130607.1
  630.   Content-Type: text/plain
  631.   Tcn: choice
  632.   Content-location: tsthtm/tst.1
  633.   Vary: negotiate,accept
  634.   Alternates: {"tst.1" 0.8 {type text/plain } {language en }},
  635.   {"tst.2" 0.3 {type tex/plain } {language fr } {features tables [abc def] }
  636.   {description "The French Version"}},
  637.   {"/gene_test?" 1 {type application/octet-stream } {language ru } 
  638.   {charset cyrillic }}
  639.   Content-Language: en
  640.   Content-length: 18
  641.   Cache-control: public
  642.  
  643. Notes:
  644.   * Since * appears in the Negotiate: header, SRE-http will 
  645.     attempt the default server side negotiation.  The Accept: text/plain
  646.     is the only information used, and the explicit q=0.8 of the first
  647.     entry beats the explicit 0.3 of the second entry.  The implicit
  648.     q=1.0 of the third entry is irrelevant, since the third entry's
  649.     content-type is not text/plain
  650.   * the Alternates: header has been reformatted (it is actually on one 
  651.     long line).
  652.   * The contents of tsthtm/tst.1, which has a size of 18 characters, 
  653.     is sent as the body of the response. 
  654.  
  655.  
  656. Alternatively, if the client does not want the server to resolve the
  657. variant:
  658.  
  659.    GET /tsthtm/tsthtm.neg  HTTP/1.1
  660.    HOST:foo.bar.net
  661.    Negotiate: vlist,*
  662.    Accept: text/plain
  663.    Accept-language: fr
  664.  
  665. which yields:
  666.    HTTP/1.1 300 Multiple Choices
  667.    Date: Sat, 26 Jun 1999 14:01:20 GMT
  668.    Server: GoServe/2.52 ;130607.1
  669.    Tcn: list
  670.    Etag: 990626095912_324;7964E38D
  671.    Vary: *
  672.    Alternates: {"tst.1" 0.8 {type text/plain } {language en }},
  673.    {"tst.2" 0.3 {type tex/plain } {language fr } {features tables [abc def] }
  674.    {description "The French Version"}},
  675.    {"/gene_test?" 1 {type application/octet-stream } {language ru } 
  676.    {charset cyrillic }}
  677.    Cache-Control: public
  678.  
  679. Note that the portion of the etag following the ; (the 7964E38D)
  680. is the same for both requests -- it's the "variant list validator"
  681. which, since the Alternates: header is the same, is also the same.
  682.  
  683.  
  684.