* Detect infinite recursions in `nickel doc`
This commit fixes an issue where legit recursive configurations cause
infinite recursion when trying to extract their documentation. Indeed,
`nickel doc` calls to `eval_record_spine`, which is unable to detect
loops that span multiple evaluation step (an evaluation step is
evaluating one field to a weak head normal form).
This commit changes `eval_record_spine` and related methods to lock (in
practice just flip a bit in the thunk's state) the active thunks, that
is the thunks of parents of the field that we are currently evaluating.
If we ever come across a thunk that is already locked, the field is left
unevaluated, avoiding infinite recursion.
* Fix clippy warning
* Fix typo in code comment
Update various flake inputs and the flake.lock file. Adapt the flake.nix
file, as well as the Rust source code, to accomodate the latest changes
(new clippy warnings, etc.).
Topiary is getting hard to use from the flake, because there are two
conflicting versions: the one that is pulled from Nix to be used in the
CI (checking that files are properly formatted), and the one built into
Nickel via cargo. Both must agree (or at least there might be a
difference in formatting between the two if they aren't the same
version). Since the addition of dynamic loading of grammars, latest
Topiary has become harder to build from Nix.
To avoid all those pitfalls, this commit gets rid of the Topiary as a
flake input, and use `nickel format` instead, ensuring that the
formatting is consistent. As a consequence, Topiary isn't included in
the development shell anymore, but it's arguably not an issue: it was
included before `nickel format`, as we needed a third party formatter,
but now one can just build Nickel locally with their preferred method
and use `nickel format`.
* Doctests
* Add a custom_transform method
* Make the vm private again
* Update doc
* Add some snapshot tests
* Split out closurized and non-closurized variants of eval_record_spine
* Fix doc link
* Add some docs, but not sure where they should go
* Make report_as_str honor the color setting
* Separate the stdout and stderr outputs more intentionally
* Commit the other snapshots
* Explicit imports
* explicit import: more changes.
* Rename typ to format
* Bring back the fallback
* Implement pretty-printer part
* Fix compilation of NLP
* Document imports
* Apply suggestions from code review
Co-authored-by: Yann Hamdaoui <yann.hamdaoui@gmail.com>
* minor fix
* explicit imports: add tests
* explicit imports: support importing the same file with different formats
* fmt
* Reinforce explicit imports test against some whitespace changes.
---------
Co-authored-by: Yann Hamdaoui <yann.hamdaoui@gmail.com>
* Fix contract equality unsound on records
Contract equality code used to flat out ignore all of the metadata of a
fields, including contract annotations, which is obviously entirely
wrong. This means that `{foo | String}` and `{foo | Number}` was deemed
equal and deduplicated as the same contract.
This commit fixes the issue by comparing the metadata as well. Contract
labels are a subtle matter, and they are the only part that is ignored
by the contract equality code.
* Add comparison of label's type_environment for safety
* Update core/src/typecheck/eq.rs
Co-authored-by: jneem <joeneeman@gmail.com>
* Add integration test for contract dedup unsoundness
---------
Co-authored-by: jneem <joeneeman@gmail.com>
* add structured output formats for `nickel query`.
WIP on interface
WIP
WIP
WIP.
Fix CI; improve impl Serialize for MergePriority
remove `Default` impl for `ExportFormatCommon`
change naming.
fix clippy warning
improvements on handling markdown format
- make markdown the default export format
- print error message when user want to export markdown format to a file.
* prune null/empty output fields
* fix clippy warnings
* fixes
* make value field a pretty printed string
---------
Co-authored-by: Ben Yang <ben@ya.ng>
* Add attrs to let patterns
* Implement let-rec patterns
* Fix markdown
* More markdown
* Put a test in the right place
* Revert the comment change
* Review comments
* Add let blocks to the AST
* Add parsing and tests
* Fix build
* Missing insta
* Fix it again
* Add a custom parse error
* Try out smallvec
* Support multiple patterns in the ast
* Support constructing let blocks with patterns
* Fix warning
* Review comments
* WIP
* WIP
* Fix typechecking
* Add lsp tests
* Add an error for duplicate bindings in a let block
* Update the manual
* Delete the old pattern file.
* Move test to integration
* Update to latest topiary-queries
Formatting of Nickel code has been updated upstream to better anticipate
the usage of `std.contract.custom` and `std.contract.from_predicate`.
This commit updates to the latest version, and update the formatting of
the stdlib, the examples and the snippets of the manual.
* Update topiary's entry in flake.lock as well
* Format stdlib/internals and benchmarks
* Initial draft without Constant and TailVar
* Restrict visibility of RemoveErrorRow to super
* Create trait Subsume for UnifType and UnifRecordRows
* Fix problem about {a: Type}<: {a:Type;b:Type} that was not accepted
* Copy comments (general comment on subsumption and closing a record when there is a record/dictionary subsumption)
* Fix problem (it was error reporting...)
* Rename trait
Co-authored-by: Yann Hamdaoui <yann.hamdaoui@gmail.com>
* Correct spelling in comments
Co-authored-by: Yann Hamdaoui <yann.hamdaoui@gmail.com>
* Rename trait impl
* Rename trait
* Update comments
* Remove subsumption function from typecheck/mod.rs
* Add test
* Add documentation
* Rename trait (for clippy)
* Add tests
* Modify snapshot lsp
* Update comments core/src/typecheck/subtyping.rs
Co-authored-by: Yann Hamdaoui <yann.hamdaoui@gmail.com>
* Update doc/manual/typing.md
Co-authored-by: Yann Hamdaoui <yann.hamdaoui@gmail.com>
* Modify comment
* Modify comment
* Revert lsp snapshot
* Cosmetic improvements
This commit performs minor cosmetic improvements in the code handling
subtyping, mostly around comments and function interfaces.
* Update snapshot test for LSP
The support of subtyping for record types makes some types to be
instantiated earlier than before. Given the way terms are visited, when
writing something like `let f = std.array.map in ..`, `std.array.map`
used to be inferred to be of a polymorphic type `forall a b. ...` and
then only was instantiated (because record access is inferred, while the
bound expression is checked). With the new implementation, it is
instantiated as part of the subsumption rule, meaning that it'll appear
differently on the LSP.
All in all, both version of the data shown by the LSP (before this
change and after) are meaningful, in some sense. The polymorphic type is
still shown when it's part of the metadata anyway, in addition to the
inferred monomorphic type. This also doesn't change which expressions
are accepted or not. It's more of an artifact of when we visit terms,
before or after instantiation and how those visits are intertwined with
`check` and `infer`. It's not easy to revert to the previous state of
affairs, and it's in fact not necessarily a good thing either: in the
example above, the LSP would also show a polymorphic type for `f` - the
one of `map` - while in fact `f` has a monomorphic type, so you couldn't
use it in different contexts (say on an `Array Number` and later on a
`Array String`). The current version is showing the real monomorphic
nature of `f`.
---------
Co-authored-by: Yann Hamdaoui <yann.hamdaoui@gmail.com>
Co-authored-by: Yann Hamdaoui <yann.hamdaoui@tweag.io>
* Fix benchmarks on Windows
* Fix tests for Windows
+ Improve failure messages
* Add CI job for Windows
* Disable unused warning for ParseFormatError
* Add `pprof` feature to utils
* Fix and improve static contract optimizations
This commit fixes a number of issues with the optimization of contract
generation from a static type annotation. It's been introduced to take
advantage of the guarantees of static typing to simplify the generated
contract and elide a number of useless checks at run-time.
However, this optimization was too agressive as implemented: it just
turned any non-function type in a positive position to `Dyn`. Indeed,
contracts in negative position must be kept around, because they check
what's come from the (potentially untyped) external world: the fact that
a function is statically typed doesn't ensure it'll be called with the
right arguments.
The first issue is that a negative contract can hide inside something
else than an arrow type. Typically, take `let functions: Array (Number
-> Number) in (std.array.at 0 functions) "a"`. The application is
untyped, and wrongly pass a string to a function of the array. However,
the current optimization code will turn this contract to just `Dyn` at
runtime and get rid of entirely, because there's an `Array _` in
positive position. This is only valid if `_` doesn't contain any arrow
type, which it does, in this example.
Another issue stems from the sealing/unsealing symmetry of polymorphic
row contracts. Take `let id : forall r. {foo : Number; r} -> {foo :
Number; r} = fun x => x in id {foo = 1, bar = 2}`. The current version
would return `{foo = 1}`, with the `bar` field missing. The issue is
that the second `{foo : Number; r}` is a record type in positive
position, which currently gets entirely elided, giving `forall r. {foo :
Number; r} -> Dyn` as an optimized contract. The argument contract seals
anything else than `foo` in the record's tail, but there's no dual
contract to unseal it anymore, such that it just becomes invisible.
This commit implements a more complicated strategy, but which is
hopefully correct. Instead of getting rid of type constructor in
positive positions, we try to simplify their content as well, and only
if the content is simplified down to `Dyn` (or `{; Dyn}` for record
rows, etc.), we get rid of the entire constructor. Otherwise, we try to
pay only for necessary checks. For example, `{foo : Number, bar : Number
-> Number}` now gets simplified to `{bar : Number -> Dyn; Dyn}` instead
of just `Dyn` before (which was incorrect).
The full simplification rules around polymorphic row contracts are a bit
intricate and are properly detailed in the documentation of the
corresponding methods.
* Add tests (wip)
* Add tests for type simplification, fix unveiled bug
* Apply suggestions from code review
Co-authored-by: jneem <joeneeman@gmail.com>
* Move back code comments to the right position
---------
Co-authored-by: jneem <joeneeman@gmail.com>
* Pre-generate contracts
After the introduction of a proper node for types in the AST, we
switched to a lazy way of generating contract: we keep the type as it
is, and convert it to a contract only once it's actually applied. While
simpler, this approach has the drawback of potentially wasting
computations by running the contract generation code many times for the
same contract, as some metrics showed (up to 1.6 thousand times on large
codebases).
This commit add a `contract` field to `Term::Type`, and statically
generates - in the parser - the contract corresponding to a type. This
is what we used to do before the introduction of a type node. Doing so,
we only generate at most one contract per user annotation, regardless of
how many times the contract is applied at runtime.
* Pre-compile match in enum contract
This commit saves some re-compilation of the match expression generated
by contracts converted from enum types by generating the compiled
version directly instead of a match.
* Fix unused import warnings
* bencher
* backslash
* rust_criterion
* try out the tweag runner
* nix it
* try using the bencher secret
* run it on ubuntu-latest
* try the master/pr split
* huh?
* Rewrite it
* why isn't the upload running?
* test
* test
* Better workflow name
* test
* test
* test
* test
* put back the conditional
* Add docs
After the rework of the contract system that sets enum as the default
return type of most custom and builtin contracts, some additional glue
code was needed to post-process such enums (and raise blame
accordingly). This has been implemented in the new internal function
`$prepare_custom_contract`.
While this function wasn't very long or involved, measurements showed
that contract application is a code path that is taken so much that this
additional blob of pure Nickel slowed down real world example by
potentially a huge factor (up to 5-6x).
While this is the symptom of other inefficiencies related to the
contract system in general (related to pattern matching, missed caching
opportunities for contract generation, etc.), bringing back the logic of
`$prepare_custom_contract` to native code brings back the overhead
(master compared to latest stable 1.7) to something like 1.1x or 1.2x.
This commit implements this strategy, by introducing two new primops:
- `%contract/postprocess_result%` which takes an enum `[| 'Ok value,
'Error error_data |]` and either unwrap `'Ok`, or modify the label
using the `error_data` and then blame
- `%label/with_error_data%`, which is used in the previous primop
implementation but can be useful as a stand alone primop and stdlib
wrapper in the future, which takes a value `{message, notes}`, a
label, and update the label's data with the corresponding diagnostic
message and notes
Additionally, this commit tries to avoid generating terms at run-time,
but rather setup the stack directly, to further make this hot path
faster.
Many contract helpers didn't have any type nor contract themselves in
the latest stable version of Nickel. With the contract system rework,
we've added missing annotations to make sure user writing contracts
would have better error messages.
However, this isn't free: on a medium-sized benchmark (25kLoC),
`contract.apply` is called approximatevely 100k times, which has an
impact on performance. While `contract.custom` or `contract.check` needs
their contract, `contract.apply` is hard to type and thus get a rather
vague type `Dyn -> Dyn -> Dyn -> Dyn`, which doesn't add much to good
error messages.
This commit removes the contract of `std.contract.apply`, reverting back
to the 1.7 situation, which shows non trivial improvements on the
benchmark mentioned above.
* apply_as_custom -> check
After bikeshedding, it's been decided in the weekly meeting that we
should use `check` for the new variant of `contract.apply` introduced in
the latest contract system rework.
We couldn't find a meaningful name for this function: `try` and
`try_apply` would be nice, but they are deceptive because they sound
like `apply_as_custom` could catch all contract errors, while it only
makes immediate errors catchable. Also, we might introduce an actualy
`contract.try` at some point, which is able to catch contract errors.
`then` and `and_then` are reflective of how they're used in custom
contract, but that might not be the only possible usage. In the end, we
just needed something different than `apply`, and `check` was the less
bad candidate, with a slight connotation of trying something (as opposed
to `eval`).
* Fix typos in contract.check doc
This commit use the metrics infrastructure to measure many more
counters, including the number of times each primop is run, each import
is evaluated, the number of contracts deduped and more. This only
impacts the build with feature `metrics` enabled (disabled by default),
and is proving useful right now to investigate a performance
degradation.
* Add trigonometric functions, pi, e and log to the numbers module
* Refactor the new maths primop, prefix them with "number/"
* Change the prefix of the arc-trigonometric functions from "a" to "arc"
* adding constructors to subsumption rule
* Add test
* Modify test
* Add dictionary constructor subtyping and adding a test for it
* Update core/tests/integration/inputs/typecheck/dictionary_subtyping.ncl
Co-authored-by: Yann Hamdaoui <yann.hamdaoui@gmail.com>
* Modify subsumption function to clone less
---------
Co-authored-by: Yann Hamdaoui <yann.hamdaoui@gmail.com>
* Pass on the contract chapter of the manual
Since this contract chapter of the manual has been reworked a lot in
various recent PR, given the changes to the contract system. This commit
is a result of a full pass on this chapter to ensure no inconsistencies
remain.
* Update doc/manual/contracts.md
Co-authored-by: jneem <joeneeman@gmail.com>
* Update doc/manual/contracts.md
Co-authored-by: jneem <joeneeman@gmail.com>
---------
Co-authored-by: jneem <joeneeman@gmail.com>
* Add boolean contract combinators to the stdlib
This commit adds the boolean combinators `one_of`, `not` and `all_of` to
the contract module of the stdlib. They are implemented in the obvious
way, by making immediate decisions based on the immediate part of their
contract operands. The limitations and possible work arounds are
detailed in the documentation and in the manual.
* Add tests for boolean contract combinators
* Apply suggestions from code review
Co-authored-by: jneem <joeneeman@gmail.com>
* Implement review suggestions
Make a pass on the new documentation of boolean contract combinators to
implement the reviewer's suggestions.
---------
Co-authored-by: jneem <joeneeman@gmail.com>
* Split builtin contracts as immediate/delayed
This commit split the builtin contracts into explicitely separated
immediate and delayed part, as per the contract design introduced in a
previous commit. This incur broad changes, as this impact the internals
module of the stdlib, the stdlib itself, and the code generating
contracts from static types.
* Change custom contract representation (again)
After converting the builtin contracts to the immediate/delayed split
representation, a number of complications appeared. Nothing that can't
be overcome, but requiring unsatisfying ad-hoc treatments or a more
complex contract interface that wasn't easy to explain in the
documentation.
In particular, passing information between the immediate
part and the delayed part is cumbersome. Splitting the logic in two
different functions is arguably harder to understand. Contract
composition, while preserving the immediate and delayed parts, is
cumbersome as well.
In the end, it occurred that switching back to one implementation for
the whole contract, but which can return a value of type `[| 'Ok Dyn,
'Error {..} |]` achieves the same (makes the immediate part and delayed
part separable) while being much simpler both for us maintainers and for
users writing and manipulating contracts. This commit implements this
simplified representation.
* Update stdlib for new ctr repr
Update the stdlib for the new two-in-one custom contract representation
which returns an enum.
* Update tests, examples and doc for new ctr repr
After having introduced a single representation for custom contracts
(instead of a split delayed/immediate), update the various Nickel
snippets in the tests, examples and the documentation to follow this new
API.
* Record contracts and apply_as_custom
This commit adapts builtin record contracts, and thus merge in contract
mode as well, to follow the new contract representation: that is, this
commit makes record contract application to return either `'Error` for
immediate errors (the argument isn't a record or there are extra fields)
instead of blaming or an `'Ok`-wrapped result.
We also add a `apply_as_custom` operator, which preserves the
`'Ok`/`'Error` result (as opposed to `apply`) which is useful to
preserve the immediate checks when calling a contract from another
contract.
* 'Ok -> 'Ok value, use apply_as_custom instead of apply whenever mandated
* Update manual for apply vs apply_as_custom
* Fix usage of renamed of internals
* Fix double contract/custom wrapping failing tests
* Fix some failing tests
* Fix signature of std.contract.custom
* Update test snapshots
* Finish implementation of apply_as_custom
* Small broken test fixes
* Fix typing of contract/custom
* Fix manual snippets
* Fix clippy warning (useless into())
* Apply suggestions from code review
Co-authored-by: jneem <joeneeman@gmail.com>
* Apply suggestions from code review
Co-authored-by: jneem <joeneeman@gmail.com>
* Simplify documentation of contract.apply
---------
Co-authored-by: jneem <joeneeman@gmail.com>
This commit improves the macro that generates dynamic type error for
primitive operators to include the operator's name automatically from
its Display implementation instead of hardcoding it. This shouldn't have
any user-facing effect immediately but should avoid in the future (as it
has happened before) any drift between the dynamic type error messages
and the current syntax/name of primops.
* clean up outdated primitive operator names
PR #1937 recently renamed many primitive operators. It missed some
instances of the previous names, though. In particular:
- error messages
- comments
- an unused function "apply_contract" in core/src/term/mod.rs
While most of these names were only made obsolete in #1937, some of them
have been incorrect for longer, eg "%array_access%" in
core/src/term/pattern/compile.rs and "recordMap" in core/src/term/mod.rs.
I caught as many as I could find. However it's hard to be sure I got all
of them, given that some of the previous names are very general terms
like "value", "fields", "length", and "map".
The full list of renames I identifiend are as follows, formatted as
"<old name> <new name>".
First, the easy cases:
chng_pol label/flip_polarity
record_map record/map
str_trim string/trim
str_chars string/chars
str_uppercase string/uppercase
str_lowercase string/lowercase
str_length string/length
str_from to_string
num_from number/from_string
enum_from enum/from_string
str_is_match string/is_match
str_find string/find
str_find_all string/find_all
record_empty_with_tail record/empty_with_tail
label_push_diag label/push_diag
enum_unwrap_variant enum/unwrap_variant
enum_is_variant enum/is_variant
enum_get_tag enum/get_tag
apply_contract contract/apply
array_lazy_app_ctr contract/array_lazy_app
record_lazy_app_ctr contract/record_lazy_app
elem_at array/at
str_split string/split
str_contains string/contains
record_insert record/insert
record_insert_with_opts record/insert_with_opts
record_remove record/remove
record_remove_with_opts record/remove_with_opts
label_with_message label/with_message
label_with_notes label/with_notes
label_append_note label/append_note
str_replace string/replace
str_replace_regex string/replace_regex
str_substr string/substr
record_seal_tail record/seal_tail
record_unseal_tail record/unseal_tail
array_slice array/slice
Then the harder cases:
polarity label/polarity
go_dom label/go_dom
go_codom label/go_codom
go_array label/go_array
go_dict label/go_dict
embed enum/embed
map array/map
generate array/generate
length array/length
fields record/fields
fields_with_opts record/fields_with_opts
values record/values
go_field label/go_field
has_field record/has_field
has_field_with_opts record/has_field_with_opts
field_is_defined record/field_is_defined
field_is_defined_with_opts record/field_is_defined_with_opts
lookup_type_variable label/lookup_type_variable
insert_type_variable label/insert_type_variable
Finally, two cases that I didn't understand and seem to be unused:
rec_force_op op rec_force
rec_default_op op rec_default
* address code review comments
The std.contract.Equal contract needs to be lazy, which means that it
re-implement equality logic in pure Nickel code, which has proven to be
very slow (https://github.com/tweag/nickel/issues/1930).
This commit replaces the field difference operation, implemented using a
left fold, by the new builtin operator `%record/split_pair%`, which
shows a performance improvement of around 300% for the example of #1930.
* flake: remove redundant transitive dependencies
- add several more `follows` relationships for de-duplication
- update to latest rust-overlay flake which drops flake-utils dependency
- set `follows = ""` for a few unused dependencies.
See https://github.com/NixOS/nix/issues/7807
* delete `follows = ""` hacks
* delete one more `follows = ""` hack
* Fix new clippy 1.79 errors
---------
Co-authored-by: Yann Hamdaoui <yann.hamdaoui@tweag.io>
* More aggressive deduplication on hover.
Deduplicate not just the type annotations, but also the contract
annotations. Also, try to report Dyn less often.
* Add hover metadata for the field of a record.
* Review comments
* Add a comment
* Add immediate/delayed notion to the manual
* Split custom contracts in immediate and delayed part
This commit explicitly split the custom contract representation and
constructors into an immediate part, similar to a validator, and a
delayed part, which is a partial identity. The stdlib and primops are
adapted as well (`%contract/custom%` now takes two arguments, the two
parts, and `%contract/from_xxx%` operators aren't used anymore as they
are subsumed by `%contract/custom%`).
* Rework prepare_contract to be more low-level and use null comparison
* Make `%contract/get_xxx%` panic on a Type
In the long run, we want that `%contract/get_immediate%` and
`%contract/get_delayed%` works as well on types, by calling to the right
function from the internals module. However, this requires deeper
changes, and is left for future work. Since those primops have just been
introduced, there's no reason they'd be used already in the wild, so for
now, we make the implemention panic if we try to apply them to a Type.
* Update stdlib doc, manual and examples
Update various documentation to reflect the new custom contract
constructor with an immediate and a delayed part.
* Update config-gcc example with new custom contract builder
* Fix tests
* Implement review suggestions
Co-authored-by: jneem <joeneeman@gmail.com>
* Review suggestion: use concrete example for delayed checks
* Review suggestion: deduplicate custom contracts in-code doc
* Update Topiary input to avoid CI error (gitsavannah)
---------
Co-authored-by: jneem <joeneeman@gmail.com>
This is preliminary work for the rewriting of native contracts using the
(to be introduced in a coming PR) new immediate/delayed representation.
In particular, in order to efficiently implement the contracts for
static record types, we need a way to split and recombine record which
is efficient and preserves field metadata.
Those primops might be useful to efficiently implement other operations
(record differences, record projection, etc.)
* Make the LSP options configurable
Take into account the configuration sent by the client through
[`InitializeParams.initializationOptions`](https://microsoft.github.io/language-server-protocol/specifications/lsp/3.17/specification/#initializeParams).
This is currently used to set the limits for the background evaluation,
although it also creates the infrastructure for setting more things.
* Fix the doc comments for the config
* Remove a useless explicit Default instance
Replace it by the derived one (thanks clippy)
* Comment fixes
Co-Authored-By: Yann Hamdaoui <yann.hamdaoui@tweag.io>
* Simplify the nls config definition
`#[serde(default)]` applied to a whole struct is enough for it to do the
right thing with the `Default` trait. Makes the module significantly
nicer to read.
---------
Co-authored-by: Yann Hamdaoui <yann.hamdaoui@tweag.io>
* Add subsumption rule between Record/Dictionary
* Remove commented code
* Remove clone in pattern match, replaced fold by a for loop, take into account TailUnifVar and TailConstant
* Update & add comments
* Add integration tests
* Allow some function equality comparison
Relax the initial restriction on comparing functions, which is that
comparing a function to anything else error out. In practice comparing a
function to a value of some other type isn't a problem, and can be
useful to allow patterns like `if x != null then ... else ...` without
having first to check if `x` is a function, because that would fail at
runtime.
Instead, we only forbid comparison between two function-like values
(functions, match expressions and custom contracts) and between two
opaque foreign values.
* Fix typo in code comment
* Additional tests for relaxed function comparison
Check the relaxed function comparison, which errors out when trying to
compare two functions, but can compare a function to a value of a
different type (by always returning false).
Tests that functions can't be compared were already there, but this
commit adds tests that function can be compared to other values.
* Add validator as a form of custom contract
* Support validators in %contract/apply%
* Add from_validator primop and stdlib function
* Add tests for custom contract constructors
* Migrate stdlib to use validators
* Add documentation on validators
* Fix manual snippets
* Apply suggestions from code review
Co-authored-by: jneem <joeneeman@gmail.com>
---------
Co-authored-by: jneem <joeneeman@gmail.com>
* Add partial identity to custom contract type
* Use %contract/custom% in the stdlib
Use the previously introduced new primop in the stdlib, to migrate from
naked functions to wrapped custom contracts everywhere in the stdlib.
* Fix tests
* Migrate examples to use std.contract.custom
* Update the manual to use std.contract.custom
Introduce the new contract constructor std.contract.custom in the
manual, and make sure that this is now everywhere presented as the
official way of building custom contracts. The section on custom
contracts is also re-organized to make general custom contracts the last
section, and present it as a last resort rather than the default way of
building custom contracts. We also left some placeholder for to the
soon-to-come validators.
* Fix typo in code comment
* Revert std.contract.apply -> %contract/apply%
In a previous commit, after introducing %contract/custom%, the stdlib
was upgraded to use this new contract constructor. Doing so, in the
contract.unstable module, many `std.contract.apply` were turned into
`%contract/apply%` following the philosophy that the stdlib should avoid
indirection through other stdlib functions bit rather directly use
primops.
However, it turns out `%contract/apply%` is not equivalent to
`std.contract.apply`. The later also stack the current diagnostics,
while the former is really only performing a function-like application,
which does make a difference for error reporting - the version with
`%contract/apply%` could erase existing error reporting data.
This commit reverts those primops calls back to using
`std.contract.apply`.
When the evaluator in the LSP times out or overflows its stack, the
faulty file is blacklisted so that it doesn't get evaluated any more.
This blacklist used to be permanent, which is generally not desirable
since it makes the LSP unusable.
Change that to only blacklist the file for a fixed delay currently
(hardcoded at 30s).