Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

rtype --> predicate parser/compiler #62

Open
ericelliott opened this issue Jan 22, 2016 · 7 comments
Open

rtype --> predicate parser/compiler #62

ericelliott opened this issue Jan 22, 2016 · 7 comments

Comments

@ericelliott
Copy link
Owner

ericelliott commented Jan 22, 2016

Write a function that takes an rtype interface description as a string and returns an object that can be used for runtime type checking.

interface TypeChecker {
  checkInputs: Predicate,
  checkOutput: Predicate,
  checkError: Predicate
}

parseSignature(signature: String) => TypeChecker

The target function will get wrapped by a utility such as rfx. When the wrapper function gets called, it will pass inputs to checkInputs(). If it returns true, only then does the original function get called. When the function returns, its output will be similarly checked by checkOutput() before it gets returned to the original caller. If the function throws, the error will also be checked, by checkError().

Useful background:

If you're curious about types, see the introduction to types from the Stanford Compiler course.

Contributing

Start with unit tests, please. See Why I Use Tape Instead of Mocha & So Should You & Five Questions Every Unit Test Must Answer for guidance on how to write a good unit test suite.

Related issues:

@tomek-he-him
Copy link
Collaborator

No time at the moment. We have the big open issue for runtime type checking in our project at work. But I can’t predict when we get down to it.

@maiermic
Copy link

Is this example correct?

parseSignature('Number => String') => {
  checkInputs: function isNumber(value) {
    return typeof value === 'number';
  },
  checkOutput: function isString(value) {
    return typeof value === 'string';
  },
  checkError: () => true // no errors defined in signature
}

@ericelliott
Copy link
Owner Author

ericelliott commented Jul 21, 2016

@maiermic What does that look like with multiple arguments? =)

I think there are still some open questions here:

  1. How do we communicate which input to check / which input is the wrong type in case of error? A predicate only returns true or false.
  2. How does this work for generator functions?

@maiermic
Copy link

Good questions.

  1. What should happen if a check fails?
  2. We could wrap the generator object to check the type of each yielded value.

@maiermic
Copy link

What does that look like with multiple arguments?

How about this example with two parameters?

function isNumber(value) {
  return typeof value === 'number';
}

function isString(value) {
  return typeof value === 'string';
}

parseSignature('(Number, String) => String') => {
  checkInputs(...inputs) {
    return isNumber(inputs[0]) && isString(inputs[1]);
  },
  checkOutput: isString,
  checkError: () => true // no errors defined in signature
}

@maiermic
Copy link

The current suggestion for parseSignature looks like this:

parseSignature(signature: String) => TypeChecker

Regarding separation of concerns: How about splitting the functionality (signature parsing and generation of TypeChecker) into two functions?

parseSignature(signature: String) => RTypeAST
generateTypeChecker(signature: RTypeAST) => TypeChecker

@ericelliott
Copy link
Owner Author

Good suggestion. We should do that. We should also make the type checking functions return an array of TypeErrors (or emit in the generator case).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

4 participants