From: Thomas Walker Lynch Date: Mon, 29 Jun 2026 08:28:19 +0000 (+0000) Subject: working documents with pagination X-Git-Url: https://git.reasoningtechnology.com/%28%5B%5E?a=commitdiff_plain;h=63aed946dd829afad31473e0254566dc13ce936f;p=RT-Style working documents with pagination --- diff --git a/administrator/document/RT-Manuscript_locator.js b/administrator/document/RT-Manuscript_locator.js new file mode 100644 index 0000000..4a1b936 --- /dev/null +++ b/administrator/document/RT-Manuscript_locator.js @@ -0,0 +1,37 @@ +/* + direct.js + + + We have four scenarios + + immediate - used in the RT-style distribution itself (authored, consummer, staged) + direct - used in the RT-style project itself, but not in the distribution + indirect - the version all Harmony projects use + URL_only - always pulls style through a URL, a webserver must be present + +*/ + +window.RT = window.RT || {}; + +(function() { + const project_name = "RT-Style"; + const path = window.location.pathname; + const project_root_index = path.indexOf('/' + project_name + '/'); + + if (project_root_index !== -1) { + // substring(0, x) excludes the trailing slash. We must prepend it to the payload. + const absolute_project_root = path.substring(0, project_root_index + project_name.length + 1); + window.RT.dirpr_library = absolute_project_root + "/consumer/Manuscript"; + } else { + // Fallback for when served via local Python HTTP daemon from the project root + window.RT.dirpr_library = "../consumer/made/Manuscript"; + } + + document.write( + ' + - + + (.*?)', content, re.IGNORECASE) + if not title_match: + print(f"Skipping {file_path}: No title tag found.") + return + + document_title = title_match.group(1) + + new_header = f""" + + + + {document_title} + + + + + + """ + + pattern = re.compile(r'.*?\s*\s*', re.DOTALL | re.IGNORECASE) + + if not pattern.search(content): + print(f"Skipping {file_path}: Header block pattern not matched.") + return + + updated_content = pattern.sub(new_header, content, count=1) + target_path.write_text(updated_content, encoding='utf8') + print(f"Successfully updated {file_path}") + +if __name__ == '__main__': + if len(sys.argv) < 2: + print("Usage: python to_v4.py ") + sys.exit(1) + + update_header_to_v4(sys.argv[1]) diff --git a/developer/authored/Manuscript.copy/Document/RT-Manuscript_locator.js b/developer/authored/Manuscript.copy/Document/RT-Manuscript_locator.js index 9f1669f..8863939 100644 --- a/developer/authored/Manuscript.copy/Document/RT-Manuscript_locator.js +++ b/developer/authored/Manuscript.copy/Document/RT-Manuscript_locator.js @@ -14,5 +14,10 @@ window.RT = window.RT || {}; (function() { window.RT.dirpr_library = ".."; - document.write(' + - - + + - + - +

This document serves as the authoritative addendum for applying the RT code format conventions to Lisp dialects, specifically Emacs Lisp. It integrates micro-syntax rules with macro-structural organization to ensure consistency across the software ecosystem. @@ -24,15 +30,15 @@

File Architecture and Section Banners

- To maintain a predictable progression from static data to external hooks, a Lisp file is divided into standard architectural sections. Each section is introduced by an Architectural Banner. + To maintain a predictable progression from static data to external hooks, a Lisp file is divided into standard architectural sections. Each section is introduced by an Architectural Banner.

  • Utilities:General use helpers that are independent of the code in the module. Perhaps these will later be moved to a utilities library.
  • -
  • Configuration: Houses foundational parameters, constants (defconst), and global variables that dictate module behavior.
  • +
  • Configuration: Houses foundational parameters, constants (defconst), and global variables that dictate module behavior.
  • Interior code: Reserved for internal, non-exported mechanisms. This includes private helper functions, macros, and localized state variables that support the public interface but remain isolated from external dependencies.
  • API: The public boundary of the module. It contains the primary functions with stable signatures and clear contracts intended for consumption by other parts of the system.
  • -
  • Interactive: Isolates functions designed for direct human execution through the Emacs command loop, typically utilizing the (interactive) declaration.
  • +
  • Interactive: Isolates functions designed for direct human execution through the Emacs command loop, typically utilizing the (interactive) declaration.
  • Integration: Placed at the bottom of the file, this section handles side effects that wire the module into the broader environment, such as adding hooks, defining keybindings, or applying advice. It is permitted to reference the API and Interactive sections, but must never reference Interior code.
@@ -42,15 +48,15 @@

    -
  • The Prologue Block: Located at the very top of the document. It uses flush left triple semicolons ;;;. Empty triple semicolons act as vertical spacing to separate paragraphs without breaking the block format.
  • +
  • The Prologue Block: Located at the very top of the document. It uses flush left triple semicolons ;;;. Empty triple semicolons act as vertical spacing to separate paragraphs without breaking the block format.
  • The Architectural Banner: Used for major file divisions (like Configuration, API). It consists of flush left triple semicolons followed by a continuous line of dashes, a title line, and an empty triple semicolon line.
  • -
  • The Scope Header: Used to group related variables or functions within a major section. These are indented two spaces, begin with double semicolons ;;, and are followed by an empty double semicolon line for vertical padding.
  • +
  • The Scope Header: Used to group related variables or functions within a major section. These are indented two spaces, begin with double semicolons ;;, and are followed by an empty double semicolon line for vertical padding.
  • The Contract Annotation: Double semicolon comments indented two spaces, placed directly above a function definition. They specify preconditions, structural expectations, or size checks that must be true before the function is called.
  • -
  • The Trailing Tag: A single semicolon ; placed at the end of a line of executable code, used to label a specific return state or note a brief detail.
  • +
  • The Trailing Tag: A single semicolon ; placed at the end of a line of executable code, used to label a specific return state or note a brief detail.

Header case, for all RT documents and code, is an initial capital letter, and no trailing period. Acronyms and tagged code or terms keep their original capitalization or lack thereof.

@@ -59,16 +65,16 @@

Primary and Secondary Separators

- Because Emacs Lisp and Common Lisp support the hyphen character in identifiers, Lisp code utilizes snake-kebab_case. The hyphen acts as the primary word separator. The underscore is reserved strictly as a secondary separator to group logically related portions of an identifier or to denote semantic boundaries, acting as a structural namespace within the symbol (e.g., city-scape_building-height). + Because Emacs Lisp and Common Lisp support the hyphen character in identifiers, Lisp code utilizes snake-kebab_case. The hyphen acts as the primary word separator. The underscore is reserved strictly as a secondary separator to group logically related portions of an identifier or to denote semantic boundaries, acting as a structural namespace within the symbol (e.g., city-scape_building-height).

Ad Hoc Namespaces

- Emacs Lisp shares a global environment. To prevent global environment pollution, functions and global variables use the center dot (·) to separate namespace hierarchies. Spaces are omitted around the dot to ensure the symbol evaluates contiguously. + Emacs Lisp shares a global environment. To prevent global environment pollution, functions and global variables use the center dot (·) to separate namespace hierarchies. Spaces are omitted around the dot to ensure the symbol evaluates contiguously.

- + (defconst RT·first-order-list·control·continue 0) - +

Code Structure Attributes

@@ -77,25 +83,25 @@

Global Two Space Offset

- Unlike standard Emacs Lisp where top level forms like defun or setq are flush left, the entire programmatic contents of the file are indented by two spaces. + Unlike standard Emacs Lisp where top level forms like defun or setq are flush left, the entire programmatic contents of the file are indented by two spaces.

Function Call Enclosures

Lisp function calls are exempt from the multi-level enclosure padding rule. The outer parentheses forming a function call receive no padding, even when they contain nested data lists.

- + (cat 'a 'b '( 2 (4 5))) - +

Vertical Branching

- The if and while statements are expanded vertically. The operator, the condition, the true branch, and the false branch each occupy their own isolated lines. + The if and while statements are expanded vertically. The operator, the condition, the true branch, and the false branch each occupy their own isolated lines.

Isolated Binding Blocks

- In let and let* forms, the variable declaration list is pushed to its own level. The opening parenthesis sits alone on a new line. Each binding sits on its own line. The closing parenthesis sits alone, vertically aligned with the opening parenthesis. The body of the form follows on the subsequent line. + In let and let* forms, the variable declaration list is pushed to its own level. The opening parenthesis sits alone on a new line. Each binding sits on its own line. The closing parenthesis sits alone, vertically aligned with the opening parenthesis. The body of the form follows on the subsequent line.

Using let to destructure a list

@@ -107,7 +113,7 @@

When the items of a list appear one per line, i.e. for a vertical list, the closing parenthesis, and all cascading closures, appear on a line of their own at the same indention level as though an element of the list. In a sense, the innermost vertical list wins, as it will close all the vertical lists it is nested in.

- + (let ( (example_list @@ -117,7 +123,7 @@ '(6 []) ))) ... - +

A comment subsection

@@ -125,45 +131,45 @@ When a comment under a triple semicolon section forms a subsection, the comment starts at the indention level of the code, has two semicolons. After the comment there is a line at the indent level with only two semicolons. Then there is a blank line. The subsection contents follow.

- + ;; Color logic ;; - (defun RT-literal·highlight-none () + (defun RT·literal·highlight-none () nil ) - (defun RT-literal·highlight-default () + (defun RT·literal·highlight-default () 'region ) - +

one line specific comment

A single semicolon occurs after the code on the line, followed by a comment.

- + - +

Contiguous Form Cluster

When the comment adds insight into the code, the comment typically appears with two semicolons at the same indentation level above said code. There is no following blank line. All code the comment applies to then follows without intervening blank lines.

- + ;; By contract: only called when overlay is in quoted form, and null string case already handled ;; Everything from content_leftmost to content_rightmost is data, inclusive. - (setq RT-literal·describe-new-form_status (list 'new-good)) - (defun RT-literal·describe-new-form_message (status) + (setq RT·literal·describe-new-form_status (list 'new-good)) + (defun RT·literal·describe-new-form_message (status) nil ) - (defun RT-literal·describe-new-form (overlay_leftmost content_rightmost_right-neighbor) + (defun RT·literal·describe-new-form (overlay_leftmost content_rightmost_right-neighbor) (let* ( ... ) ... ))) - +

API Design Conventions

@@ -178,16 +184,16 @@

    -
  • Tape: An array of cells. A tape has a leftmost cell and a rightmost cell.
  • -
  • Rightmost Right-Neighbor: The cell located one position to the right of the rightmost cell. A tape area is not guaranteed to have a rightmost_right-neighbor, but it will always have a rightmost cell.
  • -
  • Extent: The index of the rightmost cell. The index of the leftmost cell is conventionally 0. The extent defines the required bit size of an index register. When speaking of arrays of bytes, extent is the maximum byte index.
  • -
  • Length: A count of cells in an array. Length is 1 plus extent, and can overflow an index register.
  • -
  • Size: A count of the underlying bytes, unless otherwise noted.
  • -
  • Position: An index (similar to a cursor position) that indicates a cell. Emacs positions differ mathematically from TTCA theory indexes.
  • +
  • Tape: An array of cells. A tape has a leftmost cell and a rightmost cell.
  • +
  • Rightmost Right-Neighbor: The cell located one position to the right of the rightmost cell. A tape area is not guaranteed to have a rightmost_right-neighbor, but it will always have a rightmost cell.
  • +
  • Extent: The index of the rightmost cell. The index of the leftmost cell is conventionally 0. The extent defines the required bit size of an index register. When speaking of arrays of bytes, extent is the maximum byte index.
  • +
  • Length: A count of cells in an array. Length is 1 plus extent, and can overflow an index register.
  • +
  • Size: A count of the underlying bytes, unless otherwise noted.
  • +
  • Position: An index (similar to a cursor position) that indicates a cell. Emacs positions differ mathematically from TTCA theory indexes.

- The TTCA ontology is a topological description. It speaks of left, and right, of leftmost and rightmost. Time dependent terms such as first or last imply scanning/traversal. The first cell scanned could be anywhere on the tape, depending on the algorithm used for the scan or traversal. Careful, the term rightmost refers to a cell that is included on the tape. It is an inclusive bound. Today exclusive bounds are more common. Inclusive found loops often exit from the middle. + The TTCA ontology is a topological description. It speaks of left, and right, of leftmost and rightmost. Time dependent terms such as first or last imply scanning/traversal. The first cell scanned could be anywhere on the tape, depending on the algorithm used for the scan or traversal. Careful, the term rightmost refers to a cell that is included on the tape. It is an inclusive bound. Today exclusive bounds are more common. Inclusive found loops often exit from the middle.

@@ -205,7 +211,7 @@

Here is the canonical RT code format for the first/rest loop:

- + (let ( ;; 1. The "First" Work & Boundary Evaluation @@ -225,13 +231,13 @@ ;; Return the final state of the work work-successful ) - +

Elisp does not have a middle-of-loop exit, but if it did, the logic would look like this:

- + (let ( (work-successful nil) @@ -248,15 +254,15 @@ )) work-successful ) - + -

Which eliminates the need for two calls to evaluate-current-cell and has-right-neighbor. This can be done in other languages that have a loop break. (Donald Knuth argued in his 1974 paper, Structured Programming with go to Statements, that forcing programmers to duplicate code simply to satisfy a rigid while or repeat/until pre/post-test constraint was a failure of the language's expressiveness. Also discussed in the Art of Computer Programming.) +

Which eliminates the need for two calls to evaluate-current-cell and has-right-neighbor. This can be done in other languages that have a loop break. (Donald Knuth argued in his 1974 paper, Structured Programming with go to Statements, that forcing programmers to duplicate code simply to satisfy a rigid while or repeat/until pre/post-test constraint was a failure of the language's expressiveness. Also discussed in the Art of Computer Programming.)

If we are willing to us catch and throw in normal control flow, this can be done in elisp as:

- + (catch 'loop-exit (while t (let @@ -269,10 +275,10 @@ (throw 'loop-exit work-successful) (RT·TM·step machine) )))) - +

So defining:

- + (defmacro RT·loop (&rest body) "An infinite loop construct designed to be exited via RT·break." `(catch 'loop-exit @@ -284,11 +290,11 @@ "Break out of an RT·loop, optionally returning RETURN_VAL." `(throw 'loop-exit ,return_val) ) - +

Our example becomes:

- + (let ( (work-successful nil) @@ -307,13 +313,13 @@ (RT·TM·step machine) )) ) - +

Production code first/rest loop example without a middle loop break.

- + (defun RT·TM·sequence·eq (TM_substrate TM_target) (let ( @@ -337,7 +343,7 @@ )) (and are-eq (not target-has-right-neighbor)) ))) - +

If the double call code is substantial, and we do not want to use a middle break, it can be put in a helper function, and then this reduces to two calls to the helper. the helper function is called in the first part and the rest loop. If the programmer tries to trick the loop by giving the variables fake values in the first part, the first/rest pattern will be broken.

@@ -360,7 +366,7 @@

To illustrate the mathematical equivalence, here is the exact same logic written as a tail-recursive function. Note that while this form is theoretically pure, the first/rest iterative loop is strictly preferred in Emacs Lisp. Because Elisp lacks Tail Call Optimization (TCO), this recursive form would eventually exhaust the call stack and crash when traversing massive sequences.

- + (defun process-sequence-recursively (machine) (let ( @@ -381,11 +387,11 @@ ;; Base case: loop terminates, return final state work-successful ))) - +

Exercise

Show the 'production code' with a first/rest pattern using the RT macros and a middle break loop.

-
+
diff --git a/developer/document/RT-code-format.html b/developer/document/RT-code-format.html index 55eecb2..2122e67 100644 --- a/developer/document/RT-code-format.html +++ b/developer/document/RT-code-format.html @@ -1,22 +1,28 @@ + + RT code format conventions - + - - + + - + - +

This document has been evolving. Consequently there is a body of non-conforming code. Whenever we run up against it, it is nice to update it. @@ -24,27 +30,27 @@

Object vs. instance nomenclature

- It is too much of an ask to remove the word 'object' from the English language, and then set it aside and give it a esoteric technical meaning. This is why the term is often misused. So we instead talk about an interface as being a set of functions that share one or more state variables. The term instance is then a collection of such state variables and their values sitting in memory. Interface functions are usually grouped within a named container, and state variables are often grouped into a single named data structure. + It is too much of an ask to remove the word 'object' from the English language, and then set it aside and give it a esoteric technical meaning. This is why the term is often misused. So we instead talk about an interface as being a set of functions that share one or more state variables. The term instance is then a collection of such state variables and their values sitting in memory. Interface functions are usually grouped within a named container, and state variables are often grouped into a single named data structure.

- In some languages the instance occurs to the left of a lower dot (period) operator and is referred to as this from inside the interface functions. In other languages there is a convention where the instance is passed in as the first parameter to interface functions. There can also be interface functions that accept multiple instances of the same type. Bridge interfaces can be created that accept two instances potentially of different types. + In some languages the instance occurs to the left of a lower dot (period) operator and is referred to as this from inside the interface functions. In other languages there is a convention where the instance is passed in as the first parameter to interface functions. There can also be interface functions that accept multiple instances of the same type. Bridge interfaces can be created that accept two instances potentially of different types.

- Since we have released object from captivity, a programmer can talk about math objects, as things found in mathematics, and C objects, as things found in the C language, even though they are not instantiated from classes, or might not even be data. For example, the for loop is a C object. + Since we have released object from captivity, a programmer can talk about math objects, as things found in mathematics, and C objects, as things found in the C language, even though they are not instantiated from classes, or might not even be data. For example, the for loop is a C object.

Identifier names

Case

    -
  • Types, modules: PascalCase
  • -
  • Functions, variables: snake-kebab_case. If a language does not allow the - character in identifiers, then snake-kebab_case reduces to RT-code>snake_case.
  • -
  • Globals: UPPER_SNAKE-KEBAB_CASE, that, reduces to UPPER_SNAKE_CASE when the language does not allow the - character in identifiers.
  • +
  • Types, modules: PascalCase
  • +
  • Functions, variables: snake-kebab_case. If a language does not allow the - character in identifiers, then snake-kebab_case reduces to RT·code>snake_case.
  • +
  • Globals: UPPER_SNAKE-KEBAB_CASE, that, reduces to UPPER_SNAKE_CASE when the language does not allow the - character in identifiers.

Proper nouns and acronyms

- Even in PascalCase and snake-kebab_case, proper nouns and acronyms remain capitalized, as per standard English language conventions (e.g., IEEE_publication-count). + Even in PascalCase and snake-kebab_case, proper nouns and acronyms remain capitalized, as per standard English language conventions (e.g., IEEE_publication-count).

Abbreviations

@@ -57,15 +63,15 @@

Primary and secondary separator use

- When a language supports the dash, -, dash connected components are given precedence and of choice, and bind semantically higher than under score separated components. E.g. rounded_x-coordinate. + When a language supports the dash, -, dash connected components are given precedence and of choice, and bind semantically higher than under score separated components. E.g. rounded_x-coordinate.

- Otherwise, if the language does not support hyphens in identifiers (such as C, Python, and Java), we conventionally drop the nicety of multiple semantic bindings, e.g. rounded_x_coordinate. However if the distinction has high value, a double underscore and be used, rounded__x_coordinate. + Otherwise, if the language does not support hyphens in identifiers (such as C, Python, and Java), we conventionally drop the nicety of multiple semantic bindings, e.g. rounded_x_coordinate. However if the distinction has high value, a double underscore and be used, rounded__x_coordinate.

Ad hoc namespacing

- Most parsers now a allow a center dot (·) in identifiers. In languages were namespaces are not explicitly available, we use the cdot to represent a namespace. Namespaces are closely related to module names, class names, interface names, and to type names,so all are written in PascalCase. So for example, Math·rounded__x_coordinate, might be variable in the Math namespace, a function on the Math interface, etc. + Most parsers now a allow a center dot (·) in identifiers. In languages were namespaces are not explicitly available, we use the cdot to represent a namespace. Namespaces are closely related to module names, class names, interface names, and to type names,so all are written in PascalCase. So for example, Math·rounded__x_coordinate, might be variable in the Math namespace, a function on the Math interface, etc.

Component order

@@ -77,7 +83,7 @@ 'read' and 'write', are the two ends of a copy. When 'this instance' is understood as being one end of the copy, then using 'read' or 'write' makes sense. However, it is generally better to provide an external copy command. The order of arguments in a copy command are `read from source value --> write to destination value` i.e. data flows from left to write. (This is contrary to an assignment operator, which has data flowing from right to left during a copy.)

-

The term make

+

The term make

When allowed by the langauge, factory functions are called 'make'. They are not called 'create', nor 'new'.

@@ -93,10 +99,10 @@ Arguments drive the function computation. Conceptually they might change on every separate call, so they are highly dynamic. Argument variables are specified when the function is defined. Argument values are given to the function at call time.

- Values are said to be given to a function. We don't say a function takes arguments, as though a call stack could reach into memory and grab values. We use terms accept and reject of values for guard code. For a function to accept an argument value is to mean that argument value was tested and passed. As an example, we can say that a square root function only accepts values greater than or equal to zero, or that it rejects negative values. + Values are said to be given to a function. We don't say a function takes arguments, as though a call stack could reach into memory and grab values. We use terms accept and reject of values for guard code. For a function to accept an argument value is to mean that argument value was tested and passed. As an example, we can say that a square root function only accepts values greater than or equal to zero, or that it rejects negative values.

- Operators are logically functions by another name. Syntactically infix notation is often used. Operands are arguments given to an operator. + Operators are logically functions by another name. Syntactically infix notation is often used. Operands are arguments given to an operator.

Plural identifiers

@@ -106,76 +112,76 @@

    -
  • list_* / seq_* : generic ordered items / indexed items
  • -
  • Map_* / dict_* : keyed containers
  • +
  • list_* / seq_* : generic ordered items / indexed items
  • +
  • Map_* / dict_* : keyed containers

Add a type prefix when it adds clarity.

    -
  • count-of_* : number of elements
  • -
  • Bool_* : Bool type
  • -
  • flag_* : value used as a Boolean flag
  • +
  • count-of_* : number of elements
  • +
  • Bool_* : Bool type
  • +
  • flag_* : value used as a Boolean flag

Identifiers for directory/file names

    -
  • dir_* : directory name
  • -
  • dirn_* : directory name
  • -
  • dirp_* : directory path
  • -
  • dirpr_* / dirpa_* : relative / absolute directory path
  • -
  • file_* : file name
  • -
  • filen_* : file name
  • -
  • filep_* : file path
  • -
  • filepr_* / fpr_* : relative path
  • -
  • filepa_* / fpa_* : absolute path
  • -
  • fsnodn_* : file system node name -
  • fsnodp_* : file system node path -
  • fsnodpr_* / fsnpr_* : relative
  • -
  • fsnodpa_* / fsnpa_*: absolute
  • +
  • dir_* : directory name
  • +
  • dirn_* : directory name
  • +
  • dirp_* : directory path
  • +
  • dirpr_* / dirpa_* : relative / absolute directory path
  • +
  • file_* : file name
  • +
  • filen_* : file name
  • +
  • filep_* : file path
  • +
  • filepr_* / fpr_* : relative path
  • +
  • filepa_* / fpa_* : absolute path
  • +
  • fsnodn_* : file system node name +
  • fsnodp_* : file system node path +
  • fsnodpr_* / fsnpr_* : relative
  • +
  • fsnodpa_* / fsnpa_*: absolute

Comma separated lists

Horizontal comma list

The comma is preceded by a space and abuts the item it follows.

- + int x ,y ,z; - +

Vertical comma list

The comma is placed before the item on the new line, aligned with the item's indentation. This applies to all languages, including Python and C.

- + result = some_function( first_argument ,second_argument ,third_argument ); - +

Enclosure spacing

Single-level enclosures

No space padding inside the enclosure punctuation.

- + if(condition){ do_something(); } - +

Multi-level enclosures

One space of padding is applied only to the outermost enclosure punctuation.

- + if( f(g(x)) ){ do_something(); } - +

This rule is not applied to function calls in Lisp. For example, the outer parentheses forming a function call receive no padding, even when they contain nested data lists:

- + (cat 'a 'b '( 2 (4 5))) - +

Indentation

    @@ -190,58 +196,58 @@ To avoid the "String Trap" (where logic is tightly coupled to the terminal and requires string serialization to reuse) executable modules must separate the Command Line Interface from the core logic.

      -
    • Work Functions: Implement core logic. They accept and return native instances (ints, lists, paths), never look at sys.argv (or equivalent), and do not depend on being run from a command line.
    • -
    • CLI Function: The bridge between the OS and the Work Function. It is always named CLI(). It parses string arguments into native types, calls the Work Function, formats the output for the user, and translates exceptions into exit codes.
    • +
    • Work Functions: Implement core logic. They accept and return native instances (ints, lists, paths), never look at sys.argv (or equivalent), and do not depend on being run from a command line.
    • +
    • CLI Function: The bridge between the OS and the Work Function. It is always named CLI(). It parses string arguments into native types, calls the Work Function, formats the output for the user, and translates exceptions into exit codes.

    Python application

    -

    Put argument parsing and if __name__ == "__main__": in the CLI section. Keep side effects out of import time.

    +

    Put argument parsing and if __name__ == "__main__": in the CLI section. Keep side effects out of import time.

    Bash application

    -

    Bash scripts should start with #!/usr/bin/env bash and set -euo pipefail. RT-style Bash separates a small top-level CLI harness from a set of functions that implement the work. Parse arguments into variables, call a main function with explicit parameters, and avoid relying on global mutable state where possible.

    +

    Bash scripts should start with #!/usr/bin/env bash and set -euo pipefail. RT·style Bash separates a small top-level CLI harness from a set of functions that implement the work. Parse arguments into variables, call a main function with explicit parameters, and avoid relying on global mutable state where possible.

    C addendum: error handling and ownership

    • Functions should document ownership of pointers and lifetimes.
    • -
    • Prefer explicit *_count parameters over sentinel values when passing arrays.
    • +
    • Prefer explicit *_count parameters over sentinel values when passing arrays.

    Automated formatting tools

    - To ensure consistency without manual drudgery, the Harmony skeleton provides a dedicated code formatter called RTfmt. A person can find this tool in the shared/tool/ directory. + To ensure consistency without manual drudgery, the Harmony skeleton provides a dedicated code formatter called RTfmt. A person can find this tool in the shared/tool/ directory.

    The RTfmt CLI

    - RTfmt is a shallow-tokenizing formatter written in Python. It parses source code into structural blocks (strings, comments, commas, and enclosures) without needing a full Abstract Syntax Tree. This architecture allows it to safely enforce RT formatting rules across multiple languages while preserving indentation and protecting native operators. + RTfmt is a shallow-tokenizing formatter written in Python. It parses source code into structural blocks (strings, comments, commas, and enclosures) without needing a full Abstract Syntax Tree. This architecture allows it to safely enforce RT formatting rules across multiple languages while preserving indentation and protecting native operators.

      -
    • RTfmt write <file...> : Formats files in place. It performs a content comparison before writing, leaving the file modification timestamp untouched if the file is already compliant.
    • -
    • RT-formatter pipe : Reads from standard input and writes to standard output, making it ideal for editor integration.
    • -
    • --lisp : A flag that instructs the formatter to skip the outermost enclosure padding rule, honoring the Lisp function call exception.
    • +
    • RTfmt write <file...> : Formats files in place. It performs a content comparison before writing, leaving the file modification timestamp untouched if the file is already compliant.
    • +
    • RT·formatter pipe : Reads from standard input and writes to standard output, making it ideal for editor integration.
    • +
    • --lisp : A flag that instructs the formatter to skip the outermost enclosure padding rule, honoring the Lisp function call exception.

    Emacs integration

    - For Emacs users, the RT-formatter.el file provides the RT-formatter-buffer interactive command. + For Emacs users, the RT·formatter.el file provides the RT·formatter-buffer interactive command.

    - This wrapper passes the current buffer through the RT-formatter pipe command. It automatically detects Lisp-derived modes to append the --lisp flag. Furthermore, it utilizes a non-destructive buffer replacement strategy. This ensures that a programmer's cursor position, selection marks, and window scroll state remain anchored exactly where they were before the formatting occurred. + This wrapper passes the current buffer through the RT·formatter pipe command. It automatically detects Lisp-derived modes to append the --lisp flag. Furthermore, it utilizes a non-destructive buffer replacement strategy. This ensures that a programmer's cursor position, selection marks, and window scroll state remain anchored exactly where they were before the formatting occurred.

    Exercises

    Exercise 1: Comma and function call formatting

    Reformat the following C code snippet to strictly adhere to the RT code format rules.

    - + void my_function(int a, int b, int c) { int result = calculate_value(a, b, c); printf("Result: %d, a: %d, b: %d, c: %d\n", result, a, b, c); } - +

    Exercise 2: Multi-level enclosure and short stuff rule

    Reformat the following C code snippet to use the multi-level enclosure rule and the short stuff rule.

    - + if (check_permissions(user_id, file_path) && is_valid(file_path)) { for (int i = 0; i < 10; i++) { if (i % 2 == 0) { @@ -249,32 +255,32 @@ } } } - +

    Exercise 3: Identifier Naming Conventions

    - Rename the following poorly named variables to strictly adhere to the RT code format rules. Assume these are variables in a C or Python program (using standard snake_case). Pay close attention to proper nouns, acronyms, and the expanded suffix semantics. + Rename the following poorly named variables to strictly adhere to the RT code format rules. Assume these are variables in a C or Python program (using standard snake_case). Pay close attention to proper nouns, acronyms, and the expanded suffix semantics.

      -
    • A variable holding a list of addresses for HTTP servers: httpServers
    • -
    • A variable counting the total number of parsed HTML nodes: num_html_nodes
    • -
    • A custom type representing a JSON payload: json_payload
    • -
    • A boolean indicating if the NASA data download is complete: isNasaDone
    • -
    • A variable holding multiple absolute file paths for images: imageFiles
    • +
    • A variable holding a list of addresses for HTTP servers: httpServers
    • +
    • A variable counting the total number of parsed HTML nodes: num_html_nodes
    • +
    • A custom type representing a JSON payload: json_payload
    • +
    • A boolean indicating if the NASA data download is complete: isNasaDone
    • +
    • A variable holding multiple absolute file paths for images: imageFiles

    Exercise 4: Identifier naming with hyphens

    - Rename the same poorly named variables from Exercise 3, but this time assume they are written in a language that supports the hyphen (-) in identifiers. Apply the rules for primary and secondary separators, keeping in mind the structural boundary of suffixes. + Rename the same poorly named variables from Exercise 3, but this time assume they are written in a language that supports the hyphen (-) in identifiers. Apply the rules for primary and secondary separators, keeping in mind the structural boundary of suffixes.

      -
    • A variable holding a list of addresses for HTTP servers: httpServers
    • -
    • A variable counting the total number of parsed HTML nodes: num_html_nodes
    • -
    • A custom type representing a JSON payload: json_payload
    • -
    • A boolean indicating if the NASA data download is complete: isNasaDone
    • -
    • A variable holding multiple absolute file paths for images: imageFiles
    • +
    • A variable holding a list of addresses for HTTP servers: httpServers
    • +
    • A variable counting the total number of parsed HTML nodes: num_html_nodes
    • +
    • A custom type representing a JSON payload: json_payload
    • +
    • A boolean indicating if the NASA data download is complete: isNasaDone
    • +
    • A variable holding multiple absolute file paths for images: imageFiles
    - + diff --git a/developer/document/naming_file-and-directory.html b/developer/document/naming_file-and-directory.html index 07e8d67..54e8dc8 100644 --- a/developer/document/naming_file-and-directory.html +++ b/developer/document/naming_file-and-directory.html @@ -1,22 +1,28 @@ + + File and directory naming conventions - + - - + + - + - +

    Program file system objects

    @@ -30,11 +36,11 @@

    - If a file represents a module or name space, follow the same naming conventions specified for classes and name spaces in the format_RT-code.html document. + If a file represents a module or name space, follow the same naming conventions specified for classes and name spaces in the format_RT·code.html document.

    - Other program files follow the same naming conventions specified in the format_RT-code.html document for an identifier of the + Other program files follow the same naming conventions specified in the format_RT·code.html document for an identifier of the contained or related language.

    @@ -58,9 +64,9 @@

    • Who uses each file with this property. Home directories are named like this.
    • -
    • The role of the people using the file. The developer and tester directories were named in this manner.
    • +
    • The role of the people using the file. The developer and tester directories were named in this manner.
    • What program are the files for.
    • -
    • The generic category of program said files are for. We prefer the names authored and made. authored files are those written by humans or AI, while made files are products of tools.
    • +
    • The generic category of program said files are for. We prefer the names authored and made. authored files are those written by humans or AI, while made files are products of tools.

    Property indicators on files

    @@ -68,9 +74,9 @@ We add a second property to a file using dot extensions to the file's name. We can extend the dot suffix model by using multiple dot suffixes. File name extensions are used to signal to the build tools how the file is to be processed:

      -
    • .cli.c : Compiler fodder made into a stand-alone executable.
    • -
    • .lib.c : Library code source, compiled as an object file and added to the project archive.
    • -
    • .mod.c : Kernel module sources.
    • +
    • .cli.c : Compiler fodder made into a stand-alone executable.
    • +
    • .lib.c : Library code source, compiled as an object file and added to the project archive.
    • +
    • .mod.c : Kernel module sources.

    Exercises

    @@ -79,11 +85,11 @@ Rename the following poorly named files to strictly adhere to the RT naming conventions. Pay close attention to the language culture, the capitalization of acronyms, and the rule for spelling out abbreviations in outer scope identifiers.

      -
    • A C-culture makefile that builds a target library and command line interface: target-lib-cli.mk
    • -
    • A Lisp-culture source file for an HTML parsing module: html_parser_mod.el
    • -
    • A C language source file that initializes an HTTP server: init-http-srv.c
    • +
    • A C-culture makefile that builds a target library and command line interface: target-lib-cli.mk
    • +
    • A Lisp-culture source file for an HTML parsing module: html_parser_mod.el
    • +
    • A C language source file that initializes an HTTP server: init-http-srv.c
    -
    + diff --git a/developer/document/single-file_C-module-and-namespace.html b/developer/document/single-file_C-module-and-namespace.html index 61acebe..1782008 100644 --- a/developer/document/single-file_C-module-and-namespace.html +++ b/developer/document/single-file_C-module-and-namespace.html @@ -1,44 +1,50 @@ + + C modules, namespaces, and the build lifecycle - + - - + + - + - +

    Single-file C source

    - The RT C language culture abandons the traditional separation of declarations into .h header files and definitions into .c source files. A developer integrates the interface and the implementation into a single file. + The RT C language culture abandons the traditional separation of declarations into .h header files and definitions into .c source files. A developer integrates the interface and the implementation into a single file.

    - When a person includes the file using an #include directive, the file exposes only its interface. When the build system compiles the file into an object, a preprocessor macro acts as an implementation gate to compile the definitions. This keeps the source tree clean and ensures the interface and implementation never fall out of synchronization. + When a person includes the file using an #include directive, the file exposes only its interface. When the build system compiles the file into an object, a preprocessor macro acts as an implementation gate to compile the definitions. This keeps the source tree clean and ensures the interface and implementation never fall out of synchronization.

    Ad hoc namespaces

    - The C language lacks native namespaces. To prevent symbol collisions in large projects, RT code format uses a center dot (·) to denote ad hoc namespaces within identifiers. + The C language lacks native namespaces. To prevent symbol collisions in large projects, RT code format uses a center dot (·) to denote ad hoc namespaces within identifiers.

    - A programmer maps the directory structure directly to these namespaces. For example, a file located at authored/ExampleGreet/Math.lib.c belongs to the ExampleGreet namespace and defines the Math module. + A programmer maps the directory structure directly to these namespaces. For example, a file located at authored/ExampleGreet/Math.lib.c belongs to the ExampleGreet namespace and defines the Math module.

      -
    • Types and modules use PascalCase.
    • -
    • Functions and variables use snake_case.
    • +
    • Types and modules use PascalCase.
    • +
    • Functions and variables use snake_case.

    - An exported function from this module carries the full namespace and module prefix, such as ExampleGreet·Math·add. + An exported function from this module carries the full namespace and module prefix, such as ExampleGreet·Math·add.

    The implementation gate

    @@ -46,16 +52,16 @@ To achieve the single-file source pattern, the code relies on two preprocessor constructs:

      -
    • Include Guard: The entire file is wrapped in an include guard using the ·ONCE suffix. This prevents redeclaration errors if the file is included multiple times.
    • -
    • Implementation Block: The definitions are wrapped in a single #ifdef block using the exact namespace and module name. The build system dynamically injects this macro via a -D compiler flag when building the module's specific object file.
    • +
    • Include Guard: The entire file is wrapped in an include guard using the ·ONCE suffix. This prevents redeclaration errors if the file is included multiple times.
    • +
    • Implementation Block: The definitions are wrapped in a single #ifdef block using the exact namespace and module name. The build system dynamically injects this macro via a -D compiler flag when building the module's specific object file.

    Build system mechanics

    - When a consumer file, such as hello.CLI.c, contains #include "Math.lib.c", the compiler processes the file without the ExampleGreet·Math macro defined. It skips the implementation and reads only the function prototype. + When a consumer file, such as hello.CLI.c, contains #include "Math.lib.c", the compiler processes the file without the ExampleGreet·Math macro defined. It skips the implementation and reads only the function prototype.

    - When the orchestrator compiles the library object, it evaluates the target name and explicitly passes -DExampleGreet·Math to the compiler. This unlocks the gate, compiling the machine code for the definitions into Math.lib.o. + When the orchestrator compiles the library object, it evaluates the target name and explicitly passes -DExampleGreet·Math to the compiler. This unlocks the gate, compiling the machine code for the definitions into Math.lib.o.

    Example: Math.lib.c

    @@ -63,7 +69,7 @@ The following example demonstrates the complete structure.

    - + #ifndef ExampleGreet·Math·ONCE #define ExampleGreet·Math·ONCE @@ -77,27 +83,27 @@ #endif // ExampleGreet·Math #endif // ExampleGreet·Math·ONCE - +

    Cross-module dependencies

    - When one module depends on another, the developer directly includes the library source file. For example, if the Greeter module requires the Math module, the file Greeter.lib.c will contain: + When one module depends on another, the developer directly includes the library source file. For example, if the Greeter module requires the Math module, the file Greeter.lib.c will contain:

    - + #include "Math.lib.c" - +

    - Because every file is protected by a ·ONCE include guard, it is safe for multiple modules to include the same dependency. The preprocessor will expand the interface once per translation unit. + Because every file is protected by a ·ONCE include guard, it is safe for multiple modules to include the same dependency. The preprocessor will expand the interface once per translation unit.

    Information hiding

    - To define internal helper functions or private data that should not be exposed in the module's public interface, a programmer places them strictly inside the #ifdef implementation block. + To define internal helper functions or private data that should not be exposed in the module's public interface, a programmer places them strictly inside the #ifdef implementation block.

    - To prevent these internal symbols from leaking into the global namespace during linking, they must be given internal linkage. The RT skeleton provides the Local macro (defined as static in RT_global.h) for this exact purpose. + To prevent these internal symbols from leaking into the global namespace during linking, they must be given internal linkage. The RT skeleton provides the Local macro (defined as static in RT_global.h) for this exact purpose.

    - + #ifdef ExampleGreet·Math Local int internal_helper(int val){ @@ -109,47 +115,47 @@ } #endif // ExampleGreet·Math - +

    Executable entry points

    - Programs intended to be compiled into standalone executables use the .CLI.c suffix. These files consume the library modules but do not define their own namespaces or include guards, as they are never included by other files. + Programs intended to be compiled into standalone executables use the .CLI.c suffix. These files consume the library modules but do not define their own namespaces or include guards, as they are never included by other files.

    - A .CLI.c file includes the necessary .lib.c files, parses command-line arguments in the main function, and passes native data types to a dedicated CLI() function to orchestrate the core logic. + A .CLI.c file includes the necessary .lib.c files, parses command-line arguments in the main function, and passes native data types to a dedicated CLI() function to orchestrate the core logic.

    Directory structure and namespaces

    - The physical layout of the authored directory dictates how the build orchestrator finds the source code. + The physical layout of the authored directory dictates how the build orchestrator finds the source code.

      -
    • Flat Structure: If a project does not utilize namespaces, the .lib.c and .CLI.c files reside directly inside the developer/authored/ directory.
    • -
    • Namespaced Structure: If a project utilizes namespaces, the files are grouped into subdirectories matching the namespace name, such as developer/authored/ExampleGreet/.
    • +
    • Flat Structure: If a project does not utilize namespaces, the .lib.c and .CLI.c files reside directly inside the developer/authored/ directory.
    • +
    • Namespaced Structure: If a project utilizes namespaces, the files are grouped into subdirectories matching the namespace name, such as developer/authored/ExampleGreet/.

    Making the code

    - The developer compiles the code using the make wrapper script located in developer/tool/make. This script accepts two primary arguments: the build command and the target namespace. + The developer compiles the code using the make wrapper script located in developer/tool/make. This script accepts two primary arguments: the build command and the target namespace.

    - + > make <command> [namespace] - +

    - To build the ExampleGreet code, a person issues the following command from the developer workspace: + To build the ExampleGreet code, a person issues the following command from the developer workspace:

    - + > make all ExampleGreet - +

    - Behind the scenes, the make wrapper assigns the namespace to an environment variable and calls the master orchestrator makefile. The orchestrator detects the namespace, updates the source directory search path to authored/ExampleGreet, and injects the appropriate namespace macros during compilation. + Behind the scenes, the make wrapper assigns the namespace to an environment variable and calls the master orchestrator makefile. The orchestrator detects the namespace, updates the source directory search path to authored/ExampleGreet, and injects the appropriate namespace macros during compilation.

    - The orchestrator compiles the .lib.c files into object files under scratchpad/build/object/, archives them into a library file, and links the .CLI.c objects into standalone executables. The final artifacts are placed in the scratchpad/made/ directory. + The orchestrator compiles the .lib.c files into object files under scratchpad/build/object/, archives them into a library file, and links the .CLI.c objects into standalone executables. The final artifacts are placed in the scratchpad/made/ directory.

    Promoting the artifacts

    @@ -157,14 +163,14 @@ Artifacts resting in the scratchpad are volatile and private to the developer. To share the executables and libraries with the rest of the project (such as the tester or consumer roles), the developer must promote them.

    - + > promote write - +

    - The promote tool compares the contents of developer/scratchpad/made/ against consumer/made/. It atomically copies any new or updated files to the consumer workspace, stripping write permissions to enforce the immutability of the deployment target. Once promoted, the hello executable is ready for testing. + The promote tool compares the contents of developer/scratchpad/made/ against consumer/made/. It atomically copies any new or updated files to the consumer workspace, stripping write permissions to enforce the immutability of the deployment target. Once promoted, the hello executable is ready for testing.

    -
    + diff --git a/document/RT-Manuscript_locator.js b/document/RT-Manuscript_locator.js new file mode 100644 index 0000000..4a1b936 --- /dev/null +++ b/document/RT-Manuscript_locator.js @@ -0,0 +1,37 @@ +/* + direct.js + + + We have four scenarios + + immediate - used in the RT-style distribution itself (authored, consummer, staged) + direct - used in the RT-style project itself, but not in the distribution + indirect - the version all Harmony projects use + URL_only - always pulls style through a URL, a webserver must be present + +*/ + +window.RT = window.RT || {}; + +(function() { + const project_name = "RT-Style"; + const path = window.location.pathname; + const project_root_index = path.indexOf('/' + project_name + '/'); + + if (project_root_index !== -1) { + // substring(0, x) excludes the trailing slash. We must prepend it to the payload. + const absolute_project_root = path.substring(0, project_root_index + project_name.length + 1); + window.RT.dirpr_library = absolute_project_root + "/consumer/Manuscript"; + } else { + // Fallback for when served via local Python HTTP daemon from the project root + window.RT.dirpr_library = "../consumer/made/Manuscript"; + } + + document.write( + ' + + - + - +

    Purpose

    @@ -37,11 +41,11 @@

    1. Clone the Harmony project to a local directory.
    2. -
    3. Remove the .git tree.
    4. +
    5. Remove the .git tree.
    6. Rename the Harmony directory to the name of the new project.
    7. -
    8. Rename the 0pus_Harmony file to reflect the name of the new project.
    9. -
    10. Add a line to the shared/tool/version file for the new project.
    11. -
    12. git init -b core_developer_branch
    13. +
    14. Rename the 0pus_Harmony file to reflect the name of the new project.
    15. +
    16. Add a line to the shared/tool/version file for the new project.
    17. +
    18. git init -b core_developer_branch

    @@ -51,7 +55,7 @@ Leave the Harmony skeleton version in the version file, so that project administrators can understand what has changed in the skeleton over time.

    - The core_developer_branch is the branch that the core development team works on. Project releases are moved to release branches. + The core_developer_branch is the branch that the core development team works on. Project releases are moved to release branches.

    Environment setup

    @@ -59,12 +63,12 @@ Python programmers who use virtual environments will be familiar with an analogous process. The term 'virtual environment' does not invoke any hardware virtualization features; rather, it is a local environment setup. To avoid confusion, a Harmony user refers instead to the 'project setup'. The command to establish the environment is called 'setup' instead of 'activate'. Also note that in Harmony, unlike in Python, there are multiple setups available, each tailored to the specific role a person takes on.

    - As of the time of this writing, the defined roles are: administrator, consumer, developer, and tester. A person takes on a role by sourcing the top-level setup script and giving the target role as an argument. For example, in a bash shell with > as the prompt, the command is: + As of the time of this writing, the defined roles are: administrator, consumer, developer, and tester. A person takes on a role by sourcing the top-level setup script and giving the target role as an argument. For example, in a bash shell with > as the prompt, the command is:

    > . setup <role> - +

    Specifically for the developer role: @@ -72,7 +76,7 @@ > . setup developer - +

    For the administrator role: @@ -80,40 +84,40 @@ > . setup administrator - +

    - Instead of starting with a period, the source command can be spelled out explicitly, for example: + Instead of starting with a period, the source command can be spelled out explicitly, for example:

    > source setup tester - +

    - Behind the scenes, the setup script performs the following actions: + Behind the scenes, the setup script performs the following actions:

      -
    • Sources the project-wide setup (shared/tool/setup) to establish the core environment variables (e.g., REPO_HOME and PROJECT).
    • -
    • Conditionally sources shared/authored/setup (if present) to apply administrator-injected, project-specific tool configurations.
    • -
    • Dynamically sources all .init files found in the shared/linked-project/ directory.
    • -
    • Configures the PATH to include shared tools, library environments, and the specific <role>/tool directory.
    • +
    • Sources the project-wide setup (shared/tool/setup) to establish the core environment variables (e.g., REPO_HOME and PROJECT).
    • +
    • Conditionally sources shared/authored/setup (if present) to apply administrator-injected, project-specific tool configurations.
    • +
    • Dynamically sources all .init files found in the shared/linked-project/ directory.
    • +
    • Configures the PATH to include shared tools, library environments, and the specific <role>/tool directory.
    • Changes the working directory into the specified role's workspace.
    • -
    • Sources the <role>/tool/setup script. While the earlier steps apply the standard Harmony skeleton setup, this final step applies the role setup that is customized for this specific project.
    • +
    • Sources the <role>/tool/setup script. While the earlier steps apply the standard Harmony skeleton setup, this final step applies the role setup that is customized for this specific project.

    After git clone

    - Because git does not track certain artifact directories (such as consumer/ outputs), a freshly cloned repository lacks external dependencies and consumable products. Team members must perform a few steps to populate these areas. + Because git does not track certain artifact directories (such as consumer/ outputs), a freshly cloned repository lacks external dependencies and consumable products. Team members must perform a few steps to populate these areas.

    Third-party tools

    - Harmony is language agnostic. When a project makes use of project-specific C, Python, NodeJS, Java, or other tools, the project administrator configures the project to expect these tools in the shared/linked-project directory via the `.init` plugin system. + Harmony is language agnostic. When a project makes use of project-specific C, Python, NodeJS, Java, or other tools, the project administrator configures the project to expect these tools in the shared/linked-project directory via the `.init` plugin system.

    - Because multiple team members will have to repeat the third-party install process after cloning a project, the administrator should carefully document the installation steps and place the resulting documents in the administrator/document directory. The standard installation method is to clone the external tool into the parent directory alongside the project, create a symlink to it under shared/linked-project/ using the project/ parent link, and supply an .init script to manage the local environment variables. + Because multiple team members will have to repeat the third-party install process after cloning a project, the administrator should carefully document the installation steps and place the resulting documents in the administrator/document directory. The standard installation method is to clone the external tool into the parent directory alongside the project, create a symlink to it under shared/linked-project/ using the project/ parent link, and supply an .init script to manage the local environment variables.

    Consumer build

    @@ -121,10 +125,10 @@ In this section we use the term 'consumer' to mean any team member that wants to make use of the project work product. The tester will want to test it, and the consumer role will want to deploy it, etc.

    - Because compiled binaries and final layouts are not tracked in the repository, the current version of Harmony requires a work product consumer to run a local build after cloning the project. The results of the build will appear directly in the consumer/ directory. + Because compiled binaries and final layouts are not tracked in the repository, the current version of Harmony requires a work product consumer to run a local build after cloning the project. The results of the build will appear directly in the consumer/ directory.

    - To facilitate this, the developer must explicitly document the project's build and promote procedure, saving this guide as developer/document/build.html. The consumer must then read this document and execute the described steps to locally populate their consumer/ directory. + To facilitate this, the developer must explicitly document the project's build and promote procedure, saving this guide as developer/document/build.html. The consumer must then read this document and execute the described steps to locally populate their consumer/ directory.

    @@ -132,19 +136,19 @@

      -
    1. > bash
    2. -
    3. > cd <project>
    4. -
    5. > . setup developer
    6. -
    7. > build <namespace>
    8. -
    9. > promote write
    10. -
    11. > exit
    12. -
    13. > bash
    14. -
    15. > cd <project>
    16. -
    17. > . setup <role>
    18. +
    19. > bash
    20. +
    21. > cd <project>
    22. +
    23. > . setup developer
    24. +
    25. > build <namespace>
    26. +
    27. > promote write
    28. +
    29. > exit
    30. +
    31. > bash
    32. +
    33. > cd <project>
    34. +
    35. > . setup <role>

    - This sequence opens a bash shell, assumes the developer role to orchestrate the build, makes the work product, then promotes it to the consumer's workspace. The exit command drops the developer role. The last two lines put the person into the <role> workspace, typically for testing or deploying. + This sequence opens a bash shell, assumes the developer role to orchestrate the build, makes the work product, then promotes it to the consumer's workspace. The exit command drops the developer role. The last two lines put the person into the <role> workspace, typically for testing or deploying.

    @@ -153,10 +157,10 @@ This section discusses our thinking in naming the files and directories found in the Harmony skeleton.

    - A directory name is considered to be a property given to each file contained in the directory. A full path then forms a semantic sentence describing each file. + A directory name is considered to be a property given to each file contained in the directory. A full path then forms a semantic sentence describing each file.

    - Because a directory name represents a property, it is rarely plural. For example, when each and every file in a directory is a test, the directory is named test. + Because a directory name represents a property, it is rarely plural. For example, when each and every file in a directory is a test, the directory is named test.

    We run into limitations when using a conventional file system as though it were a property based file system. One limitation is that we are forced to choose a single directory name for each file. When a set of files in a directory all share the same multiple properties, we can use a compound directory name with the properties separated by an underscore, but it is impractical to specify overlapping directory groupings, i.e. we can't arbitrarily define any number of properties for a file in this manner. @@ -165,41 +169,41 @@ The following list presents each property type in order of preference when naming directories:

      -
    • Role Association (administrator, developer, tester, consumer): Identifies the persona, whether human or AI, intended to interact with the files.
    • -
    • Provenance (authored, made): Indicates whether the file was created by an intellect or mechanically produced by a tool.
    • -
    • Capability (tool, document, experiment): Describes the primary function or structural nature of the file.
    • -
    • Lifecycle State (scratchpad, stage): Denotes the persistence, volatility, or promotion status of the file.
    • -
    • Tracking Status (tracked, untracked): Specifies the version control expectations for the artifacts.
    • +
    • Role Association (administrator, developer, tester, consumer): Identifies the persona, whether human or AI, intended to interact with the files.
    • +
    • Provenance (authored, made): Indicates whether the file was created by an intellect or mechanically produced by a tool.
    • +
    • Capability (tool, document, experiment): Describes the primary function or structural nature of the file.
    • +
    • Lifecycle State (scratchpad, stage): Denotes the persistence, volatility, or promotion status of the file.
    • +
    • Tracking Status (tracked, untracked): Specifies the version control expectations for the artifacts.

    Authored, made, scratchpad, inherited

    - Files found in a directory named authored were written by project team members. They did not come with the Harmony skeleton, nor with the installation of other software. Project build tools treat authored directories as strictly read-only. Typically these files constitute the intellectual property of a project. + Files found in a directory named authored were written by project team members. They did not come with the Harmony skeleton, nor with the installation of other software. Project build tools treat authored directories as strictly read-only. Typically these files constitute the intellectual property of a project.

    - All source code that gets built into a promotion or project release must be placed in the developers' authored directory. The story is not as clean for build tools and other files. New documents go into document directories, and new tools go into the tool directories, etc. As a specific example, the developer will almost certainly edit the developer/tool/build file. + All source code that gets built into a promotion or project release must be placed in the developers' authored directory. The story is not as clean for build tools and other files. New documents go into document directories, and new tools go into the tool directories, etc. As a specific example, the developer will almost certainly edit the developer/tool/build file.

    - When the Harmony version line in the shared/tool/version file is left in place, it is straightforward for a project administrator to determine which Harmony skeleton files have been edited in a project, and which new files have been added. + When the Harmony version line in the shared/tool/version file is left in place, it is straightforward for a project administrator to determine which Harmony skeleton files have been edited in a project, and which new files have been added.

    - Files found in a directory named scratchpad are not tracked. Hence, a git clone will always return empty scratchpad directories. It is common for tools to place intermediate files on a scratchpad. It is also common for files to be staged on a scratchpad. Tools play nice and use subdirectories on the pad, so a person who is aware of those subdirectory names can use a scratchpad as a temporary directory. There is a scratchpad maintenance tool that comes with the Harmony, called unimaginatively, scratchpad. Pay attention as one of its commands is clear, and that deletes everything on the current directory's scratchpad. + Files found in a directory named scratchpad are not tracked. Hence, a git clone will always return empty scratchpad directories. It is common for tools to place intermediate files on a scratchpad. It is also common for files to be staged on a scratchpad. Tools play nice and use subdirectories on the pad, so a person who is aware of those subdirectory names can use a scratchpad as a temporary directory. There is a scratchpad maintenance tool that comes with the Harmony, called unimaginatively, scratchpad. Pay attention as one of its commands is clear, and that deletes everything on the current directory's scratchpad.

    - Third party software is installed under shared/linked-project. Other files are said to be inherited, or to be customizations. + Third party software is installed under shared/linked-project. Other files are said to be inherited, or to be customizations.

    Top-level repository layout

    - A team member will source the project setup file to take on a role. As of this writing, the supported roles are: administrator, developer, tester, and consumer. + A team member will source the project setup file to take on a role. As of this writing, the supported roles are: administrator, developer, tester, and consumer.

      -
    • administrator/ : Project-local tools and skeleton maintenance.
    • -
    • developer/ : Primary workspace for developers.
    • -
    • tester/ : Regression and validation workspace for testers.
    • -
    • consumer/ : Consumption workspace acting as the final artifact sink.
    • -
    • shared/ : Shared ecosystem tools and global environments.
    • +
    • administrator/ : Project-local tools and skeleton maintenance.
    • +
    • developer/ : Primary workspace for developers.
    • +
    • tester/ : Regression and validation workspace for testers.
    • +
    • consumer/ : Consumption workspace acting as the final artifact sink.
    • +
    • shared/ : Shared ecosystem tools and global environments.

    The administrator work area

    @@ -209,29 +213,29 @@

    The developer work area

    - This directory is entered by first going to the top-level directory of the project, then sourcing . setup developer. + This directory is entered by first going to the top-level directory of the project, then sourcing . setup developer.

      -
    • authored/ : Human-written source. Tracked by Git.
    • -
    • made/ : Tracked artifacts generated by tools (e.g., links to CLI entry points).
    • -
    • experiment/ : Try-it-here code. Short-lived spot testing.
    • -
    • scratchpad/ : Git-ignored directory. Holds all intermediate build outputs, including the staged namespace directories for promotions.
    • -
    • tool/ : Developer-specific tools (like the promote and build scripts).
    • +
    • authored/ : Human-written source. Tracked by Git.
    • +
    • made/ : Tracked artifacts generated by tools (e.g., links to CLI entry points).
    • +
    • experiment/ : Try-it-here code. Short-lived spot testing.
    • +
    • scratchpad/ : Git-ignored directory. Holds all intermediate build outputs, including the staged namespace directories for promotions.
    • +
    • tool/ : Developer-specific tools (like the promote and build scripts).

    The tester work area

    - This directory is dedicated to formal testing, including regression suites. While a developer can run and keep informal spot tests in their experiment/ directory, any experiment promoted to a formal test is moved here. This enforces the boundary between writing code and validating it. + This directory is dedicated to formal testing, including regression suites. While a developer can run and keep informal spot tests in their experiment/ directory, any experiment promoted to a formal test is moved here. This enforces the boundary between writing code and validating it.

    The shared tree

    - This directory contains ecosystem tools and global environments available to all roles. This includes the shared tool directory, as well as third-party symlinks and .init scripts required by the project. To assist in project specific modifications to the Harmony skeleton, Harmony comes with an empty shared/authored directory that is listed earlier in the executable search path than shared/tool. + This directory contains ecosystem tools and global environments available to all roles. This includes the shared tool directory, as well as third-party symlinks and .init scripts required by the project. To assist in project specific modifications to the Harmony skeleton, Harmony comes with an empty shared/authored directory that is listed earlier in the executable search path than shared/tool.

    The consumer tree

    - The consumer/ tree is where developers put work product that is ready to be consumed. The entire directory is git-ignored and treated as a transient deployment target. Artifacts arrive in the consumer/ tree only when the promote script is invoked, which performs a flat-copy from the developer's scratchpad/made directory. + The consumer/ tree is where developers put work product that is ready to be consumed. The entire directory is git-ignored and treated as a transient deployment target. Artifacts arrive in the consumer/ tree only when the promote script is invoked, which performs a flat-copy from the developer's scratchpad/made directory.

    Document directories

    @@ -239,23 +243,23 @@ There is a directory for documents that talks about the project as a whole, one for each role, one for tools that are shared among the roles, and the released work product probably comes with a document directory of its own.

      -
    • document/ : Top-level onboarding, project-wide structure, such as this document.
    • -
    • consumer/<namespace>/document/ : Documentation for end-users of made code (e.g., man pages, application manuals, library API references).
    • -
    • administrator/document/ : Documentation for maintaining the project skeleton and global tools.
    • -
    • developer/document/ : Documentation for developers, including coding standards and internal API guides.
    • -
    • tester/document/ : Documentation for testers detailing test plans and tools.
    • -
    • shared/document/ : Documentation on installing and configuring shared tools.
    • +
    • document/ : Top-level onboarding, project-wide structure, such as this document.
    • +
    • consumer/<namespace>/document/ : Documentation for end-users of made code (e.g., man pages, application manuals, library API references).
    • +
    • administrator/document/ : Documentation for maintaining the project skeleton and global tools.
    • +
    • developer/document/ : Documentation for developers, including coding standards and internal API guides.
    • +
    • tester/document/ : Documentation for testers detailing test plans and tools.
    • +
    • shared/document/ : Documentation on installing and configuring shared tools.

    - Currently, our developers write documents directly in HTML using the RT semantic tags. See the RT-Style project and the documentation there. A common approach is to copy another document and the setup.js file, then to type over the top of that other document. + Currently, our developers write documents directly in HTML using the RT semantic tags. See the RT·Style project and the documentation there. A common approach is to copy another document and the setup.js file, then to type over the top of that other document.

    Untracked directories

      -
    1. consumer/ (Excluding the base .gitignore)
    2. -
    3. shared/linked-project/ (Excluding .init and .gitignore files)
    4. -
    5. **/scratchpad/
    6. +
    7. consumer/ (Excluding the base .gitignore)
    8. +
    9. shared/linked-project/ (Excluding .init and .gitignore files)
    10. +
    11. **/scratchpad/

    Workflow

    @@ -263,16 +267,16 @@

    Developer promotion and project releases

    - As a first step, a developer creates a promotion candidate inside of the consumer/ directory. This is typically done by running build to stage the artifacts into scratchpad/made, followed by running promote write. The developer will often modify the versions of one or both of those tools that come with the Harmony skeleton. The promotion candidate remains stable until the next promotion. + As a first step, a developer creates a promotion candidate inside of the consumer/ directory. This is typically done by running build to stage the artifacts into scratchpad/made, followed by running promote write. The developer will often modify the versions of one or both of those tools that come with the Harmony skeleton. The promotion candidate remains stable until the next promotion.

    - Then the tester runs tests on the promotion candidate. Tests must only read from the consumer/ directory, though local copies can be made and edited as experiments. + Then the tester runs tests on the promotion candidate. Tests must only read from the consumer/ directory, though local copies can be made and edited as experiments.

    It is common for a developer to open a second window on his desktop, and then enter the project as a tester in that second window. The developer can then make a promotion candidate, run the tests, edit source code, and perhaps tests, and then quickly spin through the test-debug-fix-promote cycle repeatedly.

    - When the product manager determines the work product to be sufficiently reliable and feature rich, the administrator will make a project release. He will do this by creating a branch called release_v<major> and tagging it. The major release numbers go up incrementally. + When the product manager determines the work product to be sufficiently reliable and feature rich, the administrator will make a project release. He will do this by creating a branch called release_v<major> and tagging it. The major release numbers go up incrementally.

    The Harmony directory tree

    @@ -329,8 +333,8 @@ │ │ ├── project -> ../../../ │ │ ├── Python-3.12.3 -> project/Python-3.12.3 │ │ ├── Python.init - │ │ ├── RT-Style -> project/RT-Style/consumer - │ │ └── RT-Style.init + │ │ ├── RT·Style -> project/RT·Style/consumer + │ │ └── RT·Style.init │ └── tool │ ├── scratchpad │ ├── setup @@ -341,13 +345,13 @@ │ └── test_routine.sh ├── RT_Format │ ├── RT_Format - │ ├── RT-formatter.el + │ ├── RT·formatter.el │ ├── data_test-0.c │ └── data_test-1.py └── tool └── setup - + - +
    diff --git a/document/role-and-workflow_product-development.html b/document/role-and-workflow_product-development.html index d9a13e6..bede081 100644 --- a/document/role-and-workflow_product-development.html +++ b/document/role-and-workflow_product-development.html @@ -3,20 +3,24 @@ Product development roles and workflow - + + - + - +

    Roles as hats

    @@ -32,7 +36,7 @@ > . setup developer > . setup tester > . setup consumer - +

    It is common for a person to have multiple terminal sessions or IDEs open, each running under a different role environment.

    @@ -41,23 +45,23 @@

    Responsibilities:

    1. Set up the project directory and keep it in sync with the Harmony skeleton.
    2. -
    3. Maintain role environments (apart from role-specific tool/setup files).
    4. +
    5. Maintain role environments (apart from role-specific tool/setup files).
    6. Install and maintain shared and third_party tools, addressing issues with the project workflow. Note that the term "third_party" encompasses any software not authored within this specific project.

    Developer role

    Responsibilities and Boundaries:

      -
    1. Write and modify authored/ source.
    2. -
    3. Run builds and place artifacts in scratchpad/made, then execute the promote write script to copy artifacts to consumer/made for testing.
    4. -
    5. Run experiments in experiment/. These experiments can sometimes be promoted to formal tests, but there is no requirement to do so. The developer role should not blur into the tester role; experiments are informal, whereas tests are formal and retained.
    6. -
    7. Strict Boundary: A developer never writes into the tester/ directory. Instead, a developer adds tests to developer/experiment/ and offers to share them.
    8. +
    9. Write and modify authored/ source.
    10. +
    11. Run builds and place artifacts in scratchpad/made, then execute the promote write script to copy artifacts to consumer/made for testing.
    12. +
    13. Run experiments in experiment/. These experiments can sometimes be promoted to formal tests, but there is no requirement to do so. The developer role should not blur into the tester role; experiments are informal, whereas tests are formal and retained.
    14. +
    15. Strict Boundary: A developer never writes into the tester/ directory. Instead, a developer adds tests to developer/experiment/ and offers to share them.

    Tester role

    Responsibilities and Boundaries:

      -
    1. Evaluate candidates under consumer/made/ and run regression suites to confirm: +
    2. Evaluate candidates under consumer/made/ and run regression suites to confirm:
      • That the code does not crash.
      • That consumers do not have a bad experience.
      • @@ -65,21 +69,21 @@
    3. File issues and communicate feedback to the developers.
    4. -
    5. Strict Boundary: A tester never patches code in the developer/ directory. Instead, the tester files issues or proposes code fixes on a separate branch.
    6. +
    7. Strict Boundary: A tester never patches code in the developer/ directory. Instead, the tester files issues or proposes code fixes on a separate branch.

    Consumer role

    Responsibilities:

    1. Act as the end-user simulation environment.
    2. -
    3. Consume and deploy artifacts exclusively from the consumer/made/ target.
    4. +
    5. Consume and deploy artifacts exclusively from the consumer/made/ target.
    6. Never author or modify code; strictly run local builds or deployments for architecture-specific testing.
    7. Report issues. (Anyone can report an issue, and consumers regularly do).

    External roles

    - These roles drive the project forward but do not have a dedicated setup <role> workspace, as they do not directly build or test the code in that capacity. If these individuals need to interface with the code, they simply put on a workspace role hat, such as administer, developer, tester, or consumer. + These roles drive the project forward but do not have a dedicated setup <role> workspace, as they do not directly build or test the code in that capacity. If these individuals need to interface with the code, they simply put on a workspace role hat, such as administer, developer, tester, or consumer.

    Product manager

    @@ -111,12 +115,12 @@

    Promotion mechanics

    - Building and promotion are separate activities. The developer compiles and places files in developer/scratchpad/made. The developer then runs promote write to transfer those files to consumer/made. + Building and promotion are separate activities. The developer compiles and places files in developer/scratchpad/made. The developer then runs promote write to transfer those files to consumer/made.

    - The consumer/made directory is strictly an untracked deployment target. No tools are permitted to rebuild during promotion, and no builds are run directly inside the consumer made directory. + The consumer/made directory is strictly an untracked deployment target. No tools are permitted to rebuild during promotion, and no builds are run directly inside the consumer made directory.

    - +
    diff --git a/document/role-and-workflow_product-maintenance.html b/document/role-and-workflow_product-maintenance.html index 3c5959a..803e132 100644 --- a/document/role-and-workflow_product-maintenance.html +++ b/document/role-and-workflow_product-maintenance.html @@ -3,20 +3,24 @@ Product maintenance roles and workflow - + + - + - +

    Maintenance philosophy

    @@ -39,7 +43,7 @@

    - The tester team develops and maintains the regression suite, the reliability suite, and additional tests. + The tester team develops and maintains the regression suite, the reliability suite, and additional tests.

    @@ -69,7 +73,7 @@

    Core developer queue

    - This queue serves the core_developer_branch. A tester writes a test for every issue reported in this queue. Doing so isolates the defect, proves the fix, and guards against future regressions. + This queue serves the core_developer_branch. A tester writes a test for every issue reported in this queue. Doing so isolates the defect, proves the fix, and guards against future regressions.

    Released product queue

    @@ -79,7 +83,7 @@

    Triage and patching

    - Guided by the project philosophy, the triage team reviews each release queue issue to determine its impact. The team assesses whether the defect affects the core_developer_branch, assuming by default that it probably does. The team also determines if the defect is critical enough to warrant a patch on one or more active release branches. + Guided by the project philosophy, the triage team reviews each release queue issue to determine its impact. The team assesses whether the defect affects the core_developer_branch, assuming by default that it probably does. The team also determines if the defect is critical enough to warrant a patch on one or more active release branches.

    Based on this assessment, the triage team files actionable tickets in the core developer queue. A ticket explicitly specifies its target branches. A ticket will be filed against either the core developer branch, specific release branches, or a combination of both. @@ -88,12 +92,12 @@ Members of the tester team also file tickets directly into the core developer queue when they discover defects in the core branch.

    - Responsibility for resolving a ticket depends on its target. The core developer team addresses fixes required on the core_developer_branch. The branch maintenance team addresses fixes required on the release_v<major> branches. + Responsibility for resolving a ticket depends on its target. The core developer team addresses fixes required on the core_developer_branch. The branch maintenance team addresses fixes required on the release_v<major> branches.

    - When a release is patched, the branch name remains static. The administrator advances the minor release number in the shared/tool/version file and tags the commit. + When a release is patched, the branch name remains static. The administrator advances the minor release number in the shared/tool/version file and tags the commit.

    - +
    diff --git a/shared/document/RT-Manuscript_locator.js b/shared/document/RT-Manuscript_locator.js new file mode 100644 index 0000000..2f93eb7 --- /dev/null +++ b/shared/document/RT-Manuscript_locator.js @@ -0,0 +1,40 @@ +/* + direct.js + + + We have four scenarios + + immediate - used in the RT-style distribution itself (authored, consummer, staged) + direct - used in the RT-style project itself, but not in the distribution + indirect - the version all Harmony projects use + URL_only - always pulls style through a URL, a webserver must be present + +*/ + +window.RT = window.RT || {}; + +(function() { + const project_name = "RT-Style"; + const path = window.location.pathname; + const project_root_index = path.indexOf('/' + project_name + '/'); + + if (project_root_index !== -1) { + // substring(0, x) excludes the trailing slash. We must prepend it to the payload. + const absolute_project_root = path.substring(0, project_root_index + project_name.length + 1); + window.RT.dirpr_library = absolute_project_root + "/consumer/Manuscript"; + } else { + // Fallback for when served via local Python HTTP daemon from the project root + window.RT.dirpr_library = "../consumer/made/Manuscript"; + } + + document.write('