GithubHelp home page GithubHelp logo

thepeergroup / aspen Goto Github PK

View Code? Open in Web Editor NEW
60.0 4.0 7.0 1.48 MB

Aspen is a markup language for turning text into graph data (via Cypher for Neo4j).

Home Page: https://aspen-lang.org

License: MIT License

Ruby 98.82% Shell 0.11% HTML 1.07%
graphs4good cypher graph-databases neo4j

aspen's Introduction

March, 2016: If you're on an old version of Jekyll Now and run into a) build warnings or b) syntax highlighting issues caused by Jekyll 3 and GitHub Pages updates, just ✨update your _config.yml✨ and you'll be set!

Jekyll Now

Jekyll is a static site generator that's perfect for GitHub hosted blogs (Jekyll Repository)

Jekyll Now makes it easier to create your Jekyll blog, by eliminating a lot of the up front setup.

  • You don't need to touch the command line
  • You don't need to install/configure ruby, rvm/rbenv, ruby gems ☺️
  • You don't need to install runtime dependencies like markdown processors, Pygments, etc
  • If you're on Windows, this will make setting up Jekyll a lot easier
  • It's easy to try out, you can just delete your forked repository if you don't like it

In a few minutes you'll be set up with a minimal, responsive blog like the one below giving you more time to spend on writing epic blog posts!

Jekyll Now Theme Screenshot

Quick Start

Step 1) Fork Jekyll Now to your User Repository

Fork this repo, then rename the repository to yourgithubusername.github.io.

Your Jekyll blog will often be viewable immediately at https://yourgithubusername.github.io (if it's not, you can often force it to build by completing step 2)

Step 1

Step 2) Customize and view your site

Enter your site name, description, avatar and many other options by editing the _config.yml file. You can easily turn on Google Analytics tracking, Disqus commenting and social icons here too.

Making a change to _config.yml (or any file in your repository) will force GitHub Pages to rebuild your site with jekyll. Your rebuilt site will be viewable a few seconds later at https://yourgithubusername.github.io - if not, give it ten minutes as GitHub suggests and it'll appear soon

There are 3 different ways that you can make changes to your blog's files:

  1. Edit files within your new username.github.io repository in the browser at GitHub.com (shown below).
  2. Use a third party GitHub content editor, like Prose by Development Seed. It's optimized for use with Jekyll making markdown editing, writing drafts, and uploading images really easy.
  3. Clone down your repository and make updates locally, then push them to your GitHub repository.

_config.yml

Step 3) Publish your first blog post

Edit /_posts/2014-3-3-Hello-World.md to publish your first blog post. This Markdown Cheatsheet might come in handy.

First Post

You can add additional posts in the browser on GitHub.com too! Just hit the + icon in /_posts/ to create new content. Just make sure to include the front-matter block at the top of each new blog post and make sure the post's filename is in this format: year-month-day-title.md

Local Development

  1. Install Jekyll and plug-ins in one fell swoop. gem install github-pages This mirrors the plug-ins used by GitHub Pages on your local machine including Jekyll, Sass, etc.
  2. Clone down your fork git clone https://github.com/yourusername/yourusername.github.io.git
  3. Serve the site and watch for markup/sass changes jekyll serve
  4. View your website at http://127.0.0.1:4000/
  5. Commit any changes and push everything to the master branch of your GitHub user repository. GitHub Pages will then rebuild and serve your website.

Moar!

I've created a more detailed walkthrough, Build A Blog With Jekyll And GitHub Pages over at the Smashing Magazine website. Check it out if you'd like a more detailed walkthrough and some background on Jekyll. 🤘

It covers:

  • A more detailed walkthrough of setting up your Jekyll blog
  • Common issues that you might encounter while using Jekyll
  • Importing from Wordpress, using your own domain name, and blogging in your favorite editor
  • Theming in Jekyll, with Liquid templating examples
  • A quick look at Jekyll 2.0’s new features, including Sass/Coffeescript support and Collections

Jekyll Now Features

✓ Command-line free fork-first workflow, using GitHub.com to create, customize and post to your blog
✓ Fully responsive and mobile optimized base theme (Theme Demo)
✓ Sass/Coffeescript support using Jekyll 2.0
✓ Free hosting on your GitHub Pages user site
✓ Markdown blogging
✓ Syntax highlighting
✓ Disqus commenting
✓ Google Analytics integration
✓ SVG social icons for your footer
✓ 3 http requests, including your avatar

✘ No installing dependencies ✘ No need to set up local development
✘ No configuring plugins
✘ No need to spend time on theming
✘ More time to code other things ... wait ✓!

Questions?

Open an Issue and let's chat!

Other forkable themes

You can use the Quick Start workflow with other themes that are set up to be forked too! Here are some of my favorites:

Credits

Contributing

Issues and Pull Requests are greatly appreciated. If you've never contributed to an open source project before I'm more than happy to walk you through how to create a pull request.

You can start by opening an issue describing the problem that you're looking to resolve and we'll go from there.

I want to keep Jekyll Now as minimal as possible. Every line of code should be one that's useful to 90% of the people using it. Please bear that in mind when submitting feature requests. If it's not something that most people will use, it probably won't get merged. 💂‍♂️

aspen's People

Contributors

beechnut avatar dependabot[bot] avatar quadrisheriff avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar

aspen's Issues

Support single quotes

You can write a full form node like this, using double quotes,

(Person { name: "Matt", age: 31 })

but if you use single-quotes, everything will break.

(Person { name: 'Matt', age: 31 })

It feels wrong to not support single-quotes. Let's support single-quotes.

Aspen Watch

Asking someone to compile a file over and over is...too much.

The CLI (Command Line Interface) should support two operations:

  • Watching an Aspen file or folder containing Aspen files, and compiling them to Cypher files
  • Watching an Aspen file or folder, compiling to Cypher, and populating a Neo4j instance.

These commands might be available as:

$ aspen watch [file or directory] [-o --output file or directory to output to]
$ aspen watch [file or directory] [-d --database URL to Neo4j instance]

For database connections, if users want to iterate on their data, they may want to clear out the previous data so the database doesn't get cluttered with defunct entities. In order to populate the database idempotently without having to drop all the data every time, aspen watch should add a special attribute to every node and edge that indicates the element was created in an aspen watch session.

Whether data is linked to aspen watch as a whole, or a specific aspen watch session, that's up for discussion.

From Ansible:

Idempotency
An operation is idempotent if the result of performing it once is exactly the same as the result of performing it repeatedly without any intervening actions.

Aspen Watch sounds like a forest safety thing, so here's a pretty image of a fire lookout watchtower from Firewatch:

Firewatch watchtower

Support list form

Let's say we're modeling a network of consultants who work in state-based regulatory environments.

To indicate that our consultant Karl knows how to work in his three specialty states, we'd write something like:

default Person, name
default_attribute State, full_name

(Karl) [knows about] (State, Rhode Island).
(Karl) [knows about] (State, Massachusetts).
(Karl) [knows about] (State, Maine).

This is fine. We can do better.


Let's support list form.

This could come in a few different variants, and I'm undecided on which we should support, but I want Aspen to support at least one bullet form. I'm thinking A and C; or A, C, and D and in D we could support different labels. Option B feels clunky to me.

A.

(Karl) [knows about] (States: Rhode Island, Massachusetts, and Maine).

B.

(Karl) [knows about] (States:
  - Rhode Island
  - Massachusetts
  - Maine
)

C.

(Karl) [knows about] (States):
  - Rhode Island
  - Massachusetts
  - Maine

D.

(Karl) [knows about]:
  - Rhode Island (State)
  - Massachusetts (State)
  - Maine (State)

String matchers in custom grammars require quotes.

From the README, in the section on custom grammars:

String matchers will match anything in double-quotes. (Please don't use single quotes, as Aspen doesn't support them yet.)

At the moment, if you have a string matcher like

Matt works as a (string job_position) at UMass Boston.

then make sure to write the job_position in quotes, like

Matt works as a "research assistant" at UMass Boston.

If you don't, it won't match.

This will be addressed in a future update, because the quotes read as sarcastic. 😉

Let's get rid of needing those quotes. We could always make them optional, but I don't see a clear need for them at all.

Feature request: Predicate lists

Hello,

Great work with Aspen, thank you very much!. I will start experimenting with it :)

I have a suggestion, which is to borrow the 'predicate lists' feature from the turtle syntax (https://www.w3.org/TR/turtle/#sec-intro)

This allows to not repeat the starting nodes each time, by using the ';' character

So if you have


default Person, name
default_attribute Employer, company_name
reciprocal knows, is friends with

# Write out the narrative data
(Matt) [is friends with] (Brianna).
(Eliza) [knows] (Brianna).
(Matt) [is friends with] (Eliza).

(Matt) [works for] (Employer, UMass Boston).

This can be prettified to:


default Person, name
default_attribute Employer, company_name
reciprocal knows, is friends with

# Write out the narrative data
(Matt) 	[is friends with] (Brianna) ;
	[is friends with] (Eliza) ;
	[works for] (Employer, UMass Boston) .

(Eliza) [knows] (Brianna).

CLI to generate files

Task list:

  • generate narrative
  • generate grammar
  • generate sheet - should also register a script in bin/convert
  • attach - attach a Google Sheet tab for downloading and processing - should also register a script in bin/convert

Set up an "all" directive that connects every node to each other

I want to say that I work with Amber, Mica, and Moss—and that we all work with each other.

To type that out would take a lot of sentences, and even a lot of lists. Instead, I want to write something like this.

! all [works with]
  - Matt
  - Amber
  - Mica
  - Moss

This would create 4! (that's 4 factorial) works with relationships, resulting in each node connected to the other three.

Add schema protections

Working with free text, there are minimal constraints and a single typo could lead to unpleasant issues.

Let's let Aspen users add guardrails so they can only specify certain nodes and edges.

Given this discourse:

allow_only:
  nodes: Person, Employer
  edges: knows, works at
----
...

referencing any other nodes or edges in Aspen OR in Cypher templates should raise an error and prevent compilation.

A refactor, frankly, would be welcome.

This is my first time writing a language, and I write in a heavily object-oriented style, which isn't how I've heard languages are typically written.

There's some necessary complicated stuff in here, and then some less-necessary complicated stuff. A refactor would, just to clarify what's going on, would be smart.

This is a good opportunity for new contributors to read through the codebase. Get in touch if you want an explanation of anything, or if you want to team up on something.

P.S. I would have been intimidated even a few weeks ago to be contributing to a language. If you write Ruby, this should generally be approachable. We parse some text, convert that text into objects, and then do some things with those objects.

Idea: all Aspen should be renderable as Markdown

So, an idea I had is that Aspen should also be valid Markdown. That way, it can be rendered as Markdown/HTML, and it can be rendered as graph relationships.

What would it take to get there? The conventions of (nodes) and [edges] would have to change, for one, because those are links.

Support strong typing of default attributes

From the README:

One known issue is that default and default_attribute auto-type the attributes they're given, and try to make them either a string or number. So, if you pass a Massachusetts zip code like 02111 into a node in either short form or default attribute form, it will become integer 2111.

As a Massachusetts resident, I vowed never to let this happen in my software, so I intend to address this soon.

The default and default_attribute lines should support (or perhaps require!) types.

default:
  label: PostOffice
  attribute: zipcode (string)
  attributes:
    Shipment: tracking_number (string)

Add query manager

I'd like to add someplace—a queries.yml in an appropriate location—that stores plain-language queries and their Cypher equivalents. The CLI could then be used to run them, either by number or by text. There's templating built into it, so you can write a query for a specific person, etc.

$ aspen queries:list

1)  Who supervises the most people?
2)  Who does { Person } supervise?
3)  Order teams by psychological safety metrics.

$ aspen query 1
    > MATCH ... # Cypher goes here

Hickory

$ aspen query Who does Holly supervise?
    > MATCH ... # Cypher goes here

Magnolia
Cottonwood
Apple

The queries would be defined sort of like this, I imagine:

-
  name: Who does { Person } supervise?
  intake: Who does { Person a } supervise?
  query: |
    WITH (Person { name: {{{a}}} }) as supervisor ...

Simplify installation

Frankly, I'm not sure how to design this gem so its executable gets put in the global $PATH, or without needing specific versions of Ruby. The goal is to have them download something and then from the command line, be able to, without bundle exec or bin/aspen, just write:

$ aspen some-command

What can we do to dramatically simplify installation and usage?

Add adapters for common graph formats

"Not just for Neo4j anymore!"

Cypher was a major impetus for building Aspen...but it's not the only graph visualizer out there.

Getting the Aspen Editor off the ground, however, is taking a while. For the first public demos, I'd rather have everything be client-side rendered and not have to get posted to a server, then a somehow-multitenanted free Neo4j database, then returned, potentially with Cypher errors.

It would be much simpler to start if the Aspen Editor output graph data in the JSON-encoded graph format used by Sigma.js & G6, and/or GEXF. That way, we could just pipe the JSON output to Sigma or G6 instead of having to do all the Neo4j setup. Later, we can add Neo4j support.

Relatedly, #19 is asking for a feature that might be well-served by adding an ActiveGraph adapter (perhaps one that builds the code but lets the Rails app run it).

Add evaluation-unique nicknames

In a custom grammar, I want to write a few lines of Cypher which let me reference a nickname within the scope of this set of statements.

For example, I want this Aspen

default:
  attributes:
    Event: title

grammar:
  -
    match:
      - (Person a) and (Person b) met through Graphs4Good.
      - (Person a) met (Person b) at Graphs4Good.
    template: |
      {{{a}}}<-[:INCLUDES]-({{{intro:uniq}}}):Introduction)-[:INCLUDES]->{{{b}}}
      ({{{intro:uniq}}})-[:OCCURRED_AT]->(Event { title: "Graphs4Good Kickoff" })
      {{{a}}}-[:KNOWS]-{{{b}}}
----
(Karin) [organized] (Event, Graphs4Good Kickoff)

Matt and Alyssa met through Graphs4Good.
Alyssa met Joel at Graphs4Good.

to include this Cypher:

MERGE (person_matt)<-[:INCLUDES]-(intro_1:Introduction)-[:INCLUDES]->(person_alyssa)
MERGE (intro_1)-[:OCCURRED_AT]->(:Event { title: "Graphs4Good Kickoff" })
MERGE (person_matt)-[:KNOWS]-(person_alyssa)

MERGE (person_alyssa)<-[:INCLUDES]-(intro_2:Introduction)-[:INCLUDES]->(person_joel)
MERGE (intro_2)-[:OCCURRED_AT]->(Event { title: "Graphs4Good Kickoff" })
MERGE (person_alyssa)-[:KNOWS]-(person_joel)

As you can see, the nickname identifier is unique to each evaluation of the template. We can reference the nickname as a string value anywhere in the template, taking care to wrap it in parens when we reference it as a node: ({{{intro:uniq}}})-[:AND_SO_FORTH]->

The convention could be an slug (here, intro), followed by :uniq to indicate it should autoincrement the nickname to preserve uniqueness.

CLI to manage project, data

It would be nice if the CLI generated a useful project file structure, and could generate one-off things.

$ aspen new project_name -d neo4j://neo4j:pass@localhost:7474

    Generated:
    ----------
    project_name                       -> Root folder
    project_name/.aspen                -> File indicating Aspen project
    project_name/manifest.yml          -> Metadata about included files
    project_name/.env                  -> Env vars
    project_name/config/db.yml         -> Database configuration
    project_name/src/                  -> Source files
    project_name/src/convert           -> Converts non-Aspen to Aspen
    project_name/src/grammars/         -> Aspen Grammar collection
    project_name/src/prepare/          -> Folder for processing data
    project_name/src/prepare/steps.yml -> Data processing step metadata
    project_name/build/                -> Compilation is output here
    project_name/.gitignore            -> Ignoring .aspen, .env, build/

$ cd project_name
$ aspen generate org chart, roles

    Generated:
    ----------
    project_name/src/org_chart.aspen
    project_name/src/roles.aspen

In this section, it's setting up a CSV (because it's better than Aspen for this particular need) and adding a script to convert the CSV to Aspen in the build process. It's also "attaching" a Google Sheet, and downloading it and converting it to Aspen before building the output; that way, data can be updated via Google Drive.

$ aspen generate --sheet people --type Person --columns Name:String:PK Email ReportsTo:Person

    Generated:
    ----------
    project_name/src/people.csv
      with columns Name (String, Primary Key), Email (Email), ReportsTo (Person)

    Registered:
    ----------
    project_name/src/people.csv with project_name/src/convert

$ echo "API CREDENTIALS GO HERE" > config/google.yml
$ aspen attach --sheet projects --type Project --primary-key Title https://docs.google.com/document/d/GOOGLE-DOC-ID-HERE/edit#

    Attached Google Sheet:
    ----------
    Projects
      https://docs.google.com/document/d/GOOGLE-DOC-ID-HERE
      with columns Title (String, Primary Key), Description (Text), ProjectManager (Person), SubProjectOf (Project)

    Registered:
    ----------
    Projects (Google Sheet) with project_name/src/convert

In this section, it's setting up a grammar file. All grammar files are combined and added to the build.

$ aspen g grammar donations

    Generated:
    ----------
    project_name/src/grammars/donations.aspen

The validate command ensures that every file converts properly and is valid Aspen syntax.

$ aspen validate

    Prevalidated:
    -------------
    ✅ project_name/src/people.csv
    ✅ Projects (Google Sheet GOOGLE-DOC-ID-HERE...)

    Converted:
    ----------
    ✅ project_name/src/people.aspen (from project_name/src/people.csv)
    ✅ project_name/src/projects.aspen (from Google Sheet GOOGLE-DOC-ID-HERE...)

    Validated:
    ----------
    ✅ project_name/src/grammars/donations.aspen
    ✅ project_name/src/org_chart.aspen
    ✅ project_name/src/roles.aspen
    ✅ project_name/src/people.aspen

$ aspen watch

    ⚠️ WARNING: Aspen Watch is experimental, and saving a file/rebuilding the data
    will cause all of the data in the linked database to be deleted and rewritten.

    Use Ctrl+C to quit.

    Watching all files in ./manifest.yml for changes.
    Save a file to rebuild the data and push it to a Neo4j database at localhost:7474.

    To rebuild the data after changes have been made to remote documents,
    save manifest.yml.

    File changed: project_name/manifest.yml
    Checking for changes to remote data.
    Validating files    ✅
    Building Aspen      ✅
    Building Cypher     ✅
    Pushing to database ✅
    Done!

aspen as dsl for a rails app?

hi , i'm investigating using neo4j and activegraph (neo4jrb) in a rails app. I'd be interested in using aspen to seed my database and for test fixtures. Would it take much to adapt this project to conform to the ActiveGraph data? (id's specifically i think)

Can't get Aspen to compile

Hi

First off, sorry if this is a simple issue I can't solve because I am a Ruby noob! I just picked it up today morning.

Main Issue:

I am trying to make Aspen work in Windows 10. I followed all your installation instructions in your README.md. Then I tried to compile a .aspen and did this:

> cd D:\Misc_Projects\aspen #This is where I have the aspen directory which I got by forking and cloning
> bundle exec ./bin/aspen compile ./Example/example.aspen 

in Powershell. This is what I got:

bundler: command not found: ./bin/aspen
Install missing gem executables with `bundle install`

My attempts at a solve:

I did do a bundle install before running this command (as mentioned in the instructions). Anyways I tried it again, but it didn't help. In fact, I checked it with:

> bundle info aspen

and it did correctly show:

  * aspen (0.1.0)
        Summary: Aspen turns simple text into graph data, compiling it into Cypher for Neo4j graph databases.
        Homepage: https://github.com/beechnut/aspen
        Path: D:/Misc_Projects/aspen

(I am assuming this means bundle install worked properly)

Then I read the ./bin/aspen file and saw the shebang and it looks like it is trying to execute some command with the ruby interpreter. Since Windows doesn't understand the shebang I did this instead of the command in the instructions:

> bundle exec ruby ./bin/aspen compile ./Example/example.aspen

That gave me a "better" error (or is it?):

Traceback (most recent call last):
        11: from ./bin/aspen:3:in `<main>'
        10: from C:/Ruby26-x64/lib/ruby/gems/2.6.0/gems/dry-cli-0.6.0/lib/dry/cli.rb:67:in `call'
         9: from C:/Ruby26-x64/lib/ruby/gems/2.6.0/gems/dry-cli-0.6.0/lib/dry/cli.rb:114:in `perform_registry'
         8: from D:/Misc_Projects/aspen/lib/aspen/cli.rb:42:in `call'
         7: from D:/Misc_Projects/aspen/lib/aspen.rb:27:in `compile_text'
         6: from D:/Misc_Projects/aspen/lib/aspen.rb:27:in `new'
         5: from C:/Ruby26-x64/lib/ruby/gems/2.6.0/gems/dry-container-0.7.2/lib/dry/container/mixin.rb:61:in `initialize'
         4: from D:/Misc_Projects/aspen/lib/aspen/configuration.rb:14:in `initialize'
         3: from D:/Misc_Projects/aspen/lib/aspen/configuration.rb:52:in `tag_lines'
         2: from D:/Misc_Projects/aspen/lib/aspen/configuration.rb:52:in `each'
         1: from D:/Misc_Projects/aspen/lib/aspen/configuration.rb:52:in `block in tag_lines'
D:/Misc_Projects/aspen/lib/aspen/configuration.rb:85:in `tag_line': There's no configuration option that matches the line: (Aspen::ConfigurationError)

  (Matt) [is friends with] (Brianna).


Maybe it's a spelling error?

(The (Matt) [is friends with] (Brianna) line comes from example.aspen. See below.) I don't know what to do next.

Some config info:

This is the ruby version I have installed:

> ruby --version
ruby 2.6.6p146 (2020-03-31 revision 67876) [x64-mingw32]

If there is any more Ruby configuration information needed from my end, let me know. (You may have to tell me the commands to get that info too since, again, I am a Ruby noob!)

What is in example.aspen:

I don't think there is anything wrong with the example.aspen file. It is in my aspen directory in a folder called Example. example.aspen looks like this:

default Person, name
default_attribute Employer, company_name
reciprocal knows, is friends with

(Matt) [is friends with] (Brianna).
(Eliza) [knows] (Brianna).
(Matt) [is friends with] (Eliza).

(Matt) [works for] (Employer, UMass Boston).

which is basically the first example code on Aspen website.

Cyphery description blocks

Would it be valuable to have describe blocks that describe an entity, and assign all relationships and attributes to them? I think it would.

I've also got an idea for slightly more Cypher-like syntax where if we add arrows/lines, we can generate multiple expressions in a single line, obviating the need for some grammars.

describe (Bilbo)
  -[lives in]->(Place: Hobbiton)<-[contains]-(Place: Middle Earth)
  -[enemies with]-(Gollum)
  [cousins with] (Frodo)
  [friends with] (Gandalf)
  age: 111

CLI command for starting database

I'd like to add a command to start the sandbox Neo4j database and maybe guide Docker installation if Docker isn't yet installed.

$ aspen startdb

Question: Aspen in Obsidian

I have been looking for many years for an application that would combine unstructured writing (complete with bi-directional links and transclusion, etc.) with more precise property relationships. While there has been an explosion of note/tools for thought apps that support unstructured text and graph-like relationship between blocks of text, none so far allow concrete definition of entities along with explicit relationships to other entities. As a fairly nontechnical person, I assume this is because it is a very difficult thing to do. However, I was wondering if aspen's approach might be a way of bringing this to tools like obsidian which are markdown based. I actually discovered aspen through obsidian community.

Scope relationship constraints to a set of node types

Background

A person can know another person, and a person can also know a skill, fact, or topic.

If a person knows someone, they probably know each other, so you could set reciprocal: knows.

However, if a dataset says that someone knows a person and also knows a fact, then the dataset with the reciprocal setting will say that the fact knows the person! That's not right.

We should be able to scope relationships by setting what node types apply to a given rule.


Here are plain English descriptions and its Aspen discourse translation.

knows relationships between people are reciprocal, but those between a person and anything else (e.g. a fact or skill) is directed.

reciprocal: knows (Person to Person)

knows relationships are allowed between a Person node and any other node.

allow_only: knows (Person to *)

knows relationships are allowed between a Person and a Person, or between a Person and a Skill.

allow_only: knows (Person to Person, Person to Skill)

Improve tutorial documentation

The tutorial in the README was written quickly, by the author of the language. It could use a review

Does it make sense? What questions do you have while you're reading that, and how could they be addressed better in the tutorial?

This is important: If something doesn't make sense, it's not you, it's the tutorial. I want anyone from any background to get what they need to understand exactly what Aspen does and why, and how they could use it.

Also, should we leave usage instructions in the README and move the tutorial to the Wiki or the Github Pages site?

Discourse requires a "default" to be set, even when it's not needed

Steps to reproduce:

  1. Write the following Aspen to a file.
default_attribute Person, name

match
  (Person a) donated $(numeric dollar_amount) to (Person b).
to
  {{{a}}}-[:GAVE_DONATION]->(:Donation { amount: {{{dollar_amount}}} })<-[:RECEIVED_DONATION]-{{{b}}}
end
----

Matt donated $20 to Hélène.
Sarah donated $30 to Sumbul.
  1. Try to compile the file: bundle exec bin/aspen compile path/to/file.aspen

Expected
The file compiles.

Actual
I receive an error that complains that a line starting with default was not set.

Commentary
You'll notice that there are no unlabeled nodes, so default shouldn't be needed.

We do need that default_attribute line there, because we need to tell Aspen that the attribute to assign the names to is name.

Notebook Status

Curious what the status is on the notebook project that is listed on the Aspen site and/or if you have any documentation around the direction you want to take it.

My interest is coming from the perspective of personal knowledge management tools like LogSeq, AthensResearch and Obsidian. Those lack any notion of named relationships in their graph and are overly-cumbersome when it comes to querying the knowledge you've stored.

Allow non-alphanumeric symbols in node content

Original comment from https://community.neo4j.com/t/aspen-a-simple-language-for-generating-graph-data/15447/2

I attempted to use Aspen from the try.aspen-lang.org site and found 1 limitation: the markup language seems to choke on use of "_" or "-" in the node names. While this is not a big deal for "graph doodling", for some serious work (atleast for me) this would be a PITA to workaround each time. Any plans on allowing such characters in the name?


It looks like node content only allows alphanumerics. We should add support for other characters, though I'd be okay leaving out parentheses for now, just to keep the lexer & parser simple.

For a test, let's make sure this Aspen compiles (it currently doesn't):

(User: George_Lucas44) [directed] (Film: THX-1138).
(Ke$ha) [changed name to] (Name: Kesha).

no implicit conversion of Hash into String

Hi, just trying this out, following the quick start. Getting this error on aspen build using the demo data:

undefined method `close' for nil:NilClass (NoMethodError)

no implicit conversion of Hash into String(TypeError)

/Users/shawngraham/.rbenv/versions/3.0.3/lib/ruby/gems/3.0.0/gems/aspen-cli-0.1.2/lib/aspen/conversion.rb:32:in `ensure in to_aspen': undefined method `close' for nil:NilClass (NoMethodError)
	from /Users/shawngraham/.rbenv/versions/3.0.3/lib/ruby/gems/3.0.0/gems/aspen-cli-0.1.2/lib/aspen/conversion.rb:32:in `to_aspen'
	from bin/convert:14:in `<main>'
/Users/shawngraham/.rbenv/versions/3.0.3/lib/ruby/3.0.0/csv.rb:1421:in `initialize': no implicit conversion of Hash into String (TypeError)
	from /Users/shawngraham/.rbenv/versions/3.0.3/lib/ruby/3.0.0/csv.rb:1421:in `open'
	from /Users/shawngraham/.rbenv/versions/3.0.3/lib/ruby/3.0.0/csv.rb:1421:in `open'
	from /Users/shawngraham/.rbenv/versions/3.0.3/lib/ruby/gems/3.0.0/gems/aspen-cli-0.1.2/lib/aspen/conversion.rb:28:in `to_aspen'
	from bin/convert:14:in `<main>'
/Users/shawngraham/.rbenv/versions/3.0.3/lib/ruby/gems/3.0.0/gems/aspen-cli-0.1.2/lib/aspen/cli/commands/build_steps.rb:105:in `call': `bin/convert` didn't work, stopping build. See above Traceback. (RuntimeError)
	from /Users/shawngraham/.rbenv/versions/3.0.3/lib/ruby/gems/3.0.0/gems/aspen-cli-0.1.2/lib/aspen/cli/commands/build.rb:18:in `call'
	from /Users/shawngraham/.rbenv/versions/3.0.3/lib/ruby/gems/3.0.0/gems/dry-cli-0.6.0/lib/dry/cli.rb:114:in `perform_registry'
	from /Users/shawngraham/.rbenv/versions/3.0.3/lib/ruby/gems/3.0.0/gems/dry-cli-0.6.0/lib/dry/cli.rb:67:in `call'
	from /Users/shawngraham/.rbenv/versions/3.0.3/lib/ruby/gems/3.0.0/gems/aspen-cli-0.1.2/bin/aspen:3:in `<top (required)>'
	from /Users/shawngraham/.rbenv/versions/3.0.3/bin/aspen:25:in `load'
	from /Users/shawngraham/.rbenv/versions/3.0.3/bin/aspen:25:in `<main>'

Thanks!

Move aspen-lang.org into a folder here

I'd like to include the website for aspen-lang.org, which is already hosted on Github Pages, in a folder in this repository.

Part of the rationale is to make sure the website and documentation have parity by having website doctests.

Support comments

From #12, there are comments in some of the examples, but Aspen doesn't technically support comments yet.

At minimum, add support for full-line comments.
Ideally, add inline comments as well.

Figure out how custom statements could output to multiple graph formats

Okay, first things first, the compiler really wants Formatter objects instead of this string handling here.

Second and most importantly, we need to figure out how to support custom statements for various output formats.

Parse the Cypher and do something with it
Parse the Cypher (maybe with libcypher-parser) and render JSON or GEXF with the output. Use FFI to get the output into Ruby. May be difficult to implement, but easier on the authors.

Custom formatter per language
Custom formatter is scoped to a specific output format, so you write a template and then outputs for JSON, GEXF, and/or Cypher, whichever you're using. Maybe this is what we start with for now; I'd like to get Neo4j out of the Aspen Editor stack. Relatively simple to implement but requires more writing on the authors' part, which is antithetical to the goals of Aspen.

Introduce an abstraction
Have an abstracted graph templating language that looks like Cypher but isn't, perhaps a subset. This would require long-term support, and be quite complex, and would introduce quite a few limitations because it can't support full Cypher.

Generated cql for large datasets chokes Neo4j

I've started building a large aspen file with 1000+ lines which results in a generated .cql with ~2000 lines. I'm using Neo4j Desktop so I paste the query in the .cql file into Neo4j browser to run. The query run fails with the following error:
There is not enough stack size to perform the current task. Increasing the JVM stack size works but then you hit the same error when the aspen size increases further.

Would it be possible to have a commandline switch to break up the generated cql query into chunks which can be batched ? I found some useful info here for batching queries:
https://medium.com/neo4j/5-tips-tricks-for-fast-batched-updates-of-graph-structures-with-neo4j-and-cypher-73c7f693c8cc

Make CLI location-agnostic

If you're not in the root directory, CLI commands run into issues, like not being able to find config files.

/project_folder $ aspen push
-> OK

/project_folder $ cd src
/project_folder/src $ aspen push
-> Error

Instead, the CLI should work when it's anywhere inside an Aspen project.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.