Blame lenses/build.aug

Packit Service a2ae7a
(*
Packit Service a2ae7a
Module: Build
Packit Service a2ae7a
   Generic functions to build lenses
Packit Service a2ae7a
Packit Service a2ae7a
Author: Raphael Pinson <raphink@gmail.com>
Packit Service a2ae7a
Packit Service a2ae7a
About: License
Packit Service a2ae7a
  This file is licensed under the LGPL v2+, like the rest of Augeas.
Packit Service a2ae7a
Packit Service a2ae7a
About: Reference
Packit Service a2ae7a
  This file provides generic functions to build Augeas lenses
Packit Service a2ae7a
*)
Packit Service a2ae7a
Packit Service a2ae7a
Packit Service a2ae7a
module Build =
Packit Service a2ae7a
Packit Service a2ae7a
let eol = Util.eol
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * Group:               GENERIC CONSTRUCTIONS
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: brackets
Packit Service a2ae7a
 *   Put a lens inside brackets
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     l:lens   - the left bracket lens
Packit Service a2ae7a
 *     r: lens  - the right bracket lens
Packit Service a2ae7a
 *     lns:lens - the lens to put inside brackets
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let brackets (l:lens) (r:lens) (lns:lens) = l . lns . r
Packit Service a2ae7a
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * Group:             LIST CONSTRUCTIONS
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: list
Packit Service a2ae7a
 *   Build a list of identical lenses separated with a given separator
Packit Service a2ae7a
 *   (at least 2 elements)
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     lns:lens - the lens to repeat in the list
Packit Service a2ae7a
 *     sep:lens - the separator lens, which can be taken from the <Sep> module
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let list (lns:lens) (sep:lens) = lns . ( sep . lns )+
Packit Service a2ae7a
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: opt_list
Packit Service a2ae7a
 *   Same as <list>, but there might be only one element in the list
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     lns:lens - the lens to repeat in the list
Packit Service a2ae7a
 *     sep:lens - the separator lens, which can be taken from the <Sep> module
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let opt_list (lns:lens) (sep:lens) = lns . ( sep . lns )*
Packit Service a2ae7a
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * Group:                   LABEL OPERATIONS
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: xchg
Packit Service a2ae7a
 *   Replace a pattern with a different label in the tree,
Packit Service a2ae7a
 *   thus emulating a key but allowing to replace the keyword
Packit Service a2ae7a
 *   with a different value than matched
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     m:regexp - the pattern to match
Packit Service a2ae7a
 *     d:string - the default value when a node in created
Packit Service a2ae7a
 *     l:string - the label to apply for such nodes
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let xchg (m:regexp) (d:string) (l:string) = del m d . label l
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: xchgs
Packit Service a2ae7a
 *   Same as <xchg>, but the pattern is the default string
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     m:string - the string to replace, also used as default
Packit Service a2ae7a
 *     l:string - the label to apply for such nodes
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let xchgs (m:string) (l:string) = xchg m m l
Packit Service a2ae7a
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * Group:                   SUBNODE CONSTRUCTIONS
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: key_value_line
Packit Service a2ae7a
 *   A subnode with a keyword, a separator and a storing lens,
Packit Service a2ae7a
 *   and an end of line
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     kw:regexp - the pattern to match as key
Packit Service a2ae7a
 *     sep:lens  - the separator lens, which can be taken from the <Sep> module
Packit Service a2ae7a
 *     sto:lens  - the storing lens
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let key_value_line (kw:regexp) (sep:lens) (sto:lens) =
Packit Service a2ae7a
                                   [ key kw . sep . sto . eol ]
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: key_value_line_comment
Packit Service a2ae7a
 *   Same as <key_value_line>, but allows to have a comment in the end of a line
Packit Service a2ae7a
 *   and an end of line
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     kw:regexp    - the pattern to match as key
Packit Service a2ae7a
 *     sep:lens     - the separator lens, which can be taken from the <Sep> module
Packit Service a2ae7a
 *     sto:lens     - the storing lens
Packit Service a2ae7a
 *     comment:lens - the comment lens, which can be taken from <Util>
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let key_value_line_comment (kw:regexp) (sep:lens) (sto:lens) (comment:lens) =
Packit Service a2ae7a
                                   [ key kw . sep . sto . (eol|comment) ]
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: key_value
Packit Service a2ae7a
 *   Same as <key_value_line>, but does not end with an end of line
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     kw:regexp - the pattern to match as key
Packit Service a2ae7a
 *     sep:lens  - the separator lens, which can be taken from the <Sep> module
Packit Service a2ae7a
 *     sto:lens  - the storing lens
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let key_value (kw: regexp) (sep:lens) (sto:lens) =
Packit Service a2ae7a
                                   [ key kw . sep . sto ]
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: key_ws_value
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Store a key/value pair where key and value are separated by whitespace
Packit Service a2ae7a
 *   and the value goes to the end of the line. Leading and trailing
Packit Service a2ae7a
 *   whitespace is stripped from the value. The end of line is consumed by
Packit Service a2ae7a
 *   this lens
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     kw:regexp - the pattern to match as key
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let key_ws_value (kw:regexp) =
Packit Service a2ae7a
  key_value_line kw Util.del_ws_spc (store Rx.space_in)
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: flag
Packit Service a2ae7a
 *   A simple flag subnode, consisting of a single key
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     kw:regexp - the pattern to match as key
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let flag (kw:regexp) = [ key kw ]
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: flag_line
Packit Service a2ae7a
 *   A simple flag line, consisting of a single key
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     kw:regexp - the pattern to match as key
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let flag_line (kw:regexp) = [ key kw . eol ]
Packit Service a2ae7a
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * Group:                   BLOCK CONSTRUCTIONS
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: block_generic
Packit Service a2ae7a
 *   A block enclosed in brackets
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     entry:lens                - the entry to be stored inside the block.
Packit Service a2ae7a
 *                                 This entry should include <Util.empty>
Packit Service a2ae7a
 *                                 or its equivalent if necessary.
Packit Service a2ae7a
 *     entry_noindent:lens       - the entry to be stored inside the block,
Packit Service a2ae7a
 *                                 without indentation.
Packit Service a2ae7a
 *                                 This entry should not include <Util.empty>
Packit Service a2ae7a
 *     entry_noeol:lens          - the entry to be stored inside the block,
Packit Service a2ae7a
 *                                 without eol.
Packit Service a2ae7a
 *                                 This entry should not include <Util.empty>
Packit Service a2ae7a
 *     entry_noindent_noeol:lens - the entry to be stored inside the block,
Packit Service a2ae7a
 *                                 without indentation or eol.
Packit Service a2ae7a
 *                                 This entry should not include <Util.empty>
Packit Service a2ae7a
 *     comment:lens              - the comment lens used in the block
Packit Service a2ae7a
 *     comment_noindent:lens     - the comment lens used in the block,
Packit Service a2ae7a
 *                                 without indentation.
Packit Service a2ae7a
 *     ldelim_re:regexp          - regexp for the left delimiter
Packit Service a2ae7a
 *     rdelim_re:regexp          - regexp for the right delimiter
Packit Service a2ae7a
 *     ldelim_default:string     - default value for the left delimiter
Packit Service a2ae7a
 *     rdelim_default:string     - default value for the right delimiter
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let block_generic
Packit Service a2ae7a
     (entry:lens) (entry_noindent:lens)
Packit Service a2ae7a
     (entry_noeol:lens) (entry_noindent_noeol:lens)
Packit Service a2ae7a
     (comment:lens) (comment_noindent:lens)
Packit Service a2ae7a
     (ldelim_re:regexp) (rdelim_re:regexp)
Packit Service a2ae7a
     (ldelim_default:string) (rdelim_default:string) =
Packit Service a2ae7a
     let block_single = entry_noindent_noeol | comment_noindent
Packit Service a2ae7a
  in let block_start  = entry_noindent | comment_noindent
Packit Service a2ae7a
  in let block_middle = (entry | comment)*
Packit Service a2ae7a
  in let block_end    = entry_noeol | comment
Packit Service a2ae7a
  in del ldelim_re ldelim_default
Packit Service a2ae7a
     . ( ( block_start . block_middle . block_end )
Packit Service a2ae7a
       | block_single )
Packit Service a2ae7a
     . del rdelim_re rdelim_default
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: block_setdefault
Packit Service a2ae7a
 *   A block enclosed in brackets
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     entry:lens - the entry to be stored inside the block.
Packit Service a2ae7a
 *                  This entry should not include <Util.empty>,
Packit Service a2ae7a
 *                  <Util.comment> or <Util.comment_noindent>,
Packit Service a2ae7a
 *                  should not be indented or finish with an eol.
Packit Service a2ae7a
 *     ldelim_re:regexp      - regexp for the left delimiter
Packit Service a2ae7a
 *     rdelim_re:regexp      - regexp for the left delimiter
Packit Service a2ae7a
 *     ldelim_default:string - default value for the left delimiter
Packit Service a2ae7a
 *     rdelim_default:string - default value for the right delimiter
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let block_setdelim (entry:lens)
Packit Service a2ae7a
                     (ldelim_re:regexp)
Packit Service a2ae7a
                     (rdelim_re:regexp)
Packit Service a2ae7a
                     (ldelim_default:string)
Packit Service a2ae7a
                     (rdelim_default:string) =
Packit Service a2ae7a
    block_generic (Util.empty | Util.indent . entry . eol)
Packit Service a2ae7a
                  (entry . eol) (Util.indent . entry) entry
Packit Service a2ae7a
                  Util.comment Util.comment_noindent
Packit Service a2ae7a
                  ldelim_re rdelim_re
Packit Service a2ae7a
                  ldelim_default rdelim_default
Packit Service a2ae7a
Packit Service a2ae7a
(* Variable: block_ldelim_re *)
Packit Service a2ae7a
let block_ldelim_re = /[ \t\n]+\{[ \t\n]*/
Packit Service a2ae7a
Packit Service a2ae7a
(* Variable: block_rdelim_re *)
Packit Service a2ae7a
let block_rdelim_re = /[ \t\n]*\}/
Packit Service a2ae7a
Packit Service a2ae7a
(* Variable: block_ldelim_default *)
Packit Service a2ae7a
let block_ldelim_default = " {\n"
Packit Service a2ae7a
Packit Service a2ae7a
(* Variable: block_rdelim_default *)
Packit Service a2ae7a
let block_rdelim_default = "}"
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: block
Packit Service a2ae7a
 *   A block enclosed in brackets
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     entry:lens - the entry to be stored inside the block.
Packit Service a2ae7a
 *                  This entry should not include <Util.empty>,
Packit Service a2ae7a
 *                  <Util.comment> or <Util.comment_noindent>,
Packit Service a2ae7a
 *                  should not be indented or finish with an eol.
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let block (entry:lens) = block_setdelim entry
Packit Service a2ae7a
                         block_ldelim_re block_rdelim_re
Packit Service a2ae7a
                         block_ldelim_default block_rdelim_default
Packit Service a2ae7a
Packit Service a2ae7a
(* Variable: block_ldelim_newlines_re *)
Packit Service a2ae7a
let block_ldelim_newlines_re = /[ \t\n]*\{([ \t\n]*\n)?/
Packit Service a2ae7a
Packit Service a2ae7a
(* Variable: block_rdelim_newlines_re *)
Packit Service a2ae7a
let block_rdelim_newlines_re = /[ \t]*\}/
Packit Service a2ae7a
Packit Service a2ae7a
(* Variable: block_ldelim_newlines_default *)
Packit Service a2ae7a
let block_ldelim_newlines_default = "\n{\n"
Packit Service a2ae7a
Packit Service a2ae7a
(* Variable: block_rdelim_newlines_default *)
Packit Service a2ae7a
let block_rdelim_newlines_default = "}"
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: block_newline
Packit Service a2ae7a
 *   A block enclosed in brackets, with newlines forced
Packit Service a2ae7a
 *   and indentation defaulting to a tab.
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     entry:lens - the entry to be stored inside the block.
Packit Service a2ae7a
 *                  This entry should not include <Util.empty>,
Packit Service a2ae7a
 *                  <Util.comment> or <Util.comment_noindent>,
Packit Service a2ae7a
 *                  should be indented and finish with an eol.
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let block_newlines (entry:lens) (comment:lens) =
Packit Service a2ae7a
   del block_ldelim_newlines_re block_ldelim_newlines_default
Packit Service a2ae7a
 . ((entry | comment) . (Util.empty | entry | comment)*)?
Packit Service a2ae7a
 . del block_rdelim_newlines_re block_rdelim_newlines_default
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: block_newlines_spc
Packit Service a2ae7a
 *   A block enclosed in brackets, with newlines forced
Packit Service a2ae7a
 *   and indentation defaulting to a tab. The opening brace
Packit Service a2ae7a
 *   must be preceded by whitespace
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     entry:lens - the entry to be stored inside the block.
Packit Service a2ae7a
 *                  This entry should not include <Util.empty>,
Packit Service a2ae7a
 *                  <Util.comment> or <Util.comment_noindent>,
Packit Service a2ae7a
 *                  should be indented and finish with an eol.
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let block_newlines_spc (entry:lens) (comment:lens) =
Packit Service a2ae7a
   del (/[ \t\n]/ . block_ldelim_newlines_re) block_ldelim_newlines_default
Packit Service a2ae7a
 . ((entry | comment) . (Util.empty | entry | comment)*)?
Packit Service a2ae7a
 . del block_rdelim_newlines_re block_rdelim_newlines_default
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: named_block
Packit Service a2ae7a
 *   A named <block> enclosed in brackets
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     kw:regexp  - the regexp for the block name
Packit Service a2ae7a
 *     entry:lens - the entry to be stored inside the block
Packit Service a2ae7a
 *                   this entry should not include <Util.empty>
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let named_block (kw:regexp) (entry:lens) = [ key kw . block entry . eol ]
Packit Service a2ae7a
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * Group:               COMBINATORICS
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: combine_two_ord
Packit Service a2ae7a
 *   Combine two lenses, ensuring first lens is first
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     a:lens - the first lens
Packit Service a2ae7a
 *     b:lens - the second lens
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let combine_two_ord (a:lens) (b:lens) = a . b
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: combine_two
Packit Service a2ae7a
 *   Combine two lenses
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     a:lens - the first lens
Packit Service a2ae7a
 *     b:lens - the second lens
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let combine_two (a:lens) (b:lens) =
Packit Service a2ae7a
  combine_two_ord a b | combine_two_ord b a
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: combine_two_opt_ord
Packit Service a2ae7a
 *   Combine two lenses optionally, ensuring first lens is first
Packit Service a2ae7a
 *   (a, and optionally b)
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     a:lens - the first lens
Packit Service a2ae7a
 *     b:lens - the second lens
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let combine_two_opt_ord (a:lens) (b:lens) = a . b?
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: combine_two_opt
Packit Service a2ae7a
 *   Combine two lenses optionally
Packit Service a2ae7a
 *   (either a, b, or both, in any order)
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     a:lens - the first lens
Packit Service a2ae7a
 *     b:lens - the second lens
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let combine_two_opt (a:lens) (b:lens) =
Packit Service a2ae7a
  combine_two_opt_ord a b | combine_two_opt_ord b a
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: combine_three_ord
Packit Service a2ae7a
 *   Combine three lenses, ensuring first lens is first
Packit Service a2ae7a
 *   (a followed by either b, c, in any order)
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     a:lens - the first lens
Packit Service a2ae7a
 *     b:lens - the second lens
Packit Service a2ae7a
 *     c:lens - the third lens
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let combine_three_ord (a:lens) (b:lens) (c:lens) =
Packit Service a2ae7a
  combine_two_ord a (combine_two b c)
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: combine_three
Packit Service a2ae7a
 *   Combine three lenses
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     a:lens - the first lens
Packit Service a2ae7a
 *     b:lens - the second lens
Packit Service a2ae7a
 *     c:lens - the third lens
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let combine_three (a:lens) (b:lens) (c:lens) =
Packit Service a2ae7a
    combine_three_ord a b c
Packit Service a2ae7a
  | combine_three_ord b a c
Packit Service a2ae7a
  | combine_three_ord c b a
Packit Service a2ae7a
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: combine_three_opt_ord
Packit Service a2ae7a
 *   Combine three lenses optionally, ensuring first lens is first
Packit Service a2ae7a
 *   (a followed by either b, c, or any of them, in any order)
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     a:lens - the first lens
Packit Service a2ae7a
 *     b:lens - the second lens
Packit Service a2ae7a
 *     c:lens - the third lens
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let combine_three_opt_ord (a:lens) (b:lens) (c:lens) =
Packit Service a2ae7a
  combine_two_opt_ord a (combine_two_opt b c)
Packit Service a2ae7a
Packit Service a2ae7a
(************************************************************************
Packit Service a2ae7a
 * View: combine_three_opt
Packit Service a2ae7a
 *   Combine three lenses optionally
Packit Service a2ae7a
 *   (either a, b, c, or any of them, in any order)
Packit Service a2ae7a
 *
Packit Service a2ae7a
 *   Parameters:
Packit Service a2ae7a
 *     a:lens - the first lens
Packit Service a2ae7a
 *     b:lens - the second lens
Packit Service a2ae7a
 *     c:lens - the third lens
Packit Service a2ae7a
 ************************************************************************)
Packit Service a2ae7a
let combine_three_opt (a:lens) (b:lens) (c:lens) =
Packit Service a2ae7a
    combine_three_opt_ord a b c
Packit Service a2ae7a
  | combine_three_opt_ord b a c
Packit Service a2ae7a
  | combine_three_opt_ord c b a