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

Make parse round-trip-able #33

Closed
cstrahan opened this issue Mar 11, 2016 · 9 comments
Closed

Make parse round-trip-able #33

cstrahan opened this issue Mar 11, 2016 · 9 comments

Comments

@cstrahan
Copy link

There are a number of tools (including one I desperately need to write) that would require the ability to parse a nix expression, transform it in some way, and then write the expression back out - all while keeping unmodified portions unchanged in the output.

I could take a stab at this, but I think I might need some hints/help.

@jwiegley
Copy link
Member

That's a great idea @cstrahan. You'll need to plumb attributes through the syntax tree that preserve knowledge like surrounding whitespace, etc. This part should be fairly easy, since we're using a Free representation.

Then, in the evaluator, you only need to preserve the attributes over any transformation (they would be abstract in that case). In the pretty printer, it would use the attributes for laying out the elements to be printed, or any other style decisions.

It's not exactly trivial, but should be straightforward, and I'm sure there are examples of something similar living out on the Web.

@cstrahan
Copy link
Author

@jwiegley I don't think trailing white space matters as much, so perhaps just tracking source spans would be sufficient (ala haskell-src-exts)?

If so, do you suppose I should add a monomorphic field (e.g. SrcSpan) to each construct? haskell-src-exts uses a polymorphic field in their annotated AST, but I don't know if we'd benefit from going that route.

@jwiegley
Copy link
Member

You shouldn't need to change the AST at all, but just change the Free type synonym.

@cstrahan
Copy link
Author

Do you mean the Fix synonym? (grepping for Free doesn't turn up anything)

Are you suggesting something like this?

data SrcSpan = SrcSpan Int Int
data Ann x f a = Ann x (f a)
type NExpr = Fix (Ann SrcSpan NExprF)

@jwiegley
Copy link
Member

Oh yeah, sorry, Fix. And yes, what you pasted is exactly what I had meant. That will give you an annotation at every level of the resulting tree.

@expipiplus1
Copy link
Collaborator

I've started working towards this in #35

@jwiegley
Copy link
Member

@cstrahan We've now merged @expipiplus1 's work, does this help you in building your tools?

@cstrahan
Copy link
Author

@jwiegley I believe so, although I've shelved that work for the time being. Thanks!

@expipiplus1
Copy link
Collaborator

For an example of this being used you can take a look here: https://github.com/expipiplus1/update-nix-fetchgit

This doens't do a round trip though, It uses the source locations to modify the underlying string.

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

No branches or pull requests

3 participants