Generic directives/plugins syntax

Actually @name is an extension so it fits perfectly the idea. The markup user would just hook to the AST and consume all Extension nodes without attributes to match users.

On the other hand !action[] could be good as well for it.

Interesting. How would this work if usernames clashed with extension names though? Say you had an extension called ā€œspoilerā€ and a user with the same name. What would @spoiler refer to?

The possibility is non-existent if the parser provides enough information to discriminate from an inline item with or without {}.

extensions then would be parsed if they contain the {} otherwise they are names.

This thread is getting out of control :smile: How about being a little pragmatic here. Letā€™s put the special structured syntax aside for a moment.

What do all languages have in common? Methods/Functions, possibly types, classes, objects, right? As extension is something that mostly programmers will work with, how about having the extension syntax be a method invocation signature? Having either a type or an instance in a parsing context, we could do :

@instance.doSomething(arg1, arg2, arg3)

or

@Singleton.doSomething(arg1, arg2, arg3)

Then youā€™d just have a plugin(s) with a several methodsā€¦ The advantage is that itā€™s pretty much self-explanatory. Name of the type/instance and method would explain what is going on and who is responsible for what. For instance :

@[content-type_xml](code/ScalaResults.scala)

I mean even this needs an entire paragraph to explain what is actually going on.

I donā€™t like the idea of generic attributes much {ā€¦}. But thatā€™s probably because I just havenā€™t had a need for that.

Good point. The parser would need to handle [] and []() as well in cases where the extra brackets arenā€™t required. I still prefer ! over @ for consistency with the image syntax. Is there a reason to use @ over !?

2 Likes

I think it depends on the particular extension. Some extentions would be for displaying particular components, e.g. a video. A writer who is not a programmer might want to easily embed a video in a blog post, for example.

Another thing to add. Order of [] & () & {} is not important, and if any is missing, it is automatically added in as an empty bracket internally.

E.g. !(file.png) ā€”(shorthand for)ā€”> !default[](file.png){}


Multiline [], (), and {} , can be supported by [[[ ... ]]], ((( ... ))), and {{{ ... }}}

e.g.

!summary[ Post-Modern Essay Generator - http://www.elsewhere.org/journal/pomo/ ]
(((
 If one examines textual narrative, one is faced with a choice: either reject constructive prematerialist theory or conclude that reality must come from the collective unconscious. 
 Many dematerialisms concerning not theory, as semanticist postdialectic theory suggests, but posttheory may be found.
)))
1 Like

I was thinking that the [] might be mandatory to reduce the probability of clashes: someone might accidentally switch a space and a ! (writing e.g. hey !wait) and be really confused if he doesnā€™t know about directives. Similarly if we go for the @-syntax: @foo could mean a username while @foo[] is an extension.

I agree that () and {} should be optional. But again, Iā€™m in favour of having them always in that order to reduce clashes and confusion on what the right order is.

1 Like

@lisak We were hoping that markdown stays declarative. Think HTML custom elements, not JavaScript function callsā€¦

I agree with mb21.

When I say !youtube[cat](https://www.youtube.com/watch?v=cbP2N1BQdYc),
what I am saying is not ā€œHow or what sequence to embed youtube linkā€ in the page.
All Iā€™m saying is that I declare that I want ā€œto embed youtube linkā€.

What this means, is I push the implementation details to whatever renders the source to display.

E.g. In html, this declaration will embeds a video player. While on printed paper this same declaration would appear as a ā€œscreenshotā€ with a QR link of the youtube video next to it.


Wikipedia: Declarative programming - Wikipedia

describing what the program should accomplish in terms of the problem domain, rather than describing how to go about accomplishing it as a sequence of the programming language primitives[2] (the how is left up to the languageā€™s implementation).

Wikipedia: Imperative programming - Wikipedia

declarative programming, which focuses on what the program should accomplish without prescribing how to do it in terms of sequences of actions to be taken.


(sidenote: Would be nice if I could just type !wikipedia[Imperative Programming] )
(Btw lisak, I really want {...}, since I do use #id often as reference anchors in a large document)

This you look at the examples for inline syntax in the first post? The (){} part is optional and usually not needed, so itā€™s mostly just @directivename[content]. Better suggestions?

Yes, unfortunately. I think jgm & co. are still busy with the core syntax and not ready to look into extensions yet.

Yes.

No. I donā€™t have better ideas. My current opinion is to implement flexible block syntax, but hardcode inline markers for each case. The only inline thing, that i really need at my projects, is math. It can be solver by something like $$ā€¦$$

At least, that should not kill my userā€™s brain until spec advice something better.

1 Like

I donā€™t remember, if i have written about it in this thread. Many people need extended syntax to add medias (video, audio). In my practice, links to youtube (and so on) are automatically replaced by embedded player. Thatā€™s very comfortable for bulk posts, because remove markup at all.

If you remove examples, related to link autoreplace, you will note, that the rest list of inlines is quite small. Im my case - math only. And math will have separate syntax in spec, i hope.

Thatā€™s why i think, that implementing bloсk syntax (without inlines) can be good step forward. If itā€™s diffucult to solve all task at once, we could split it into parts.

Thatā€™s a strategy I use. Itā€™s preferable including a references to specific sites within CommonMark. Unfortunately there is no end to the amount of sites that could be supported.

Maybe !wiki[Imperative Programming] or !encyclopaedia[Imperative Programming] instead where the behaviour is CMS specific. The content management system creator could swap out the prefered encylopaedia with another one in the future (say, if a better alternative to Wikipedia came along) and also define how the link is handled (e.g. wiki info displayed as a link to Wikipedia vs embedded in a popover). You could do a similar thing with !dictionary[Imperative] and !thesaurus[Imperative].

1 Like

That depends on project & implementations. Usually static list of 10-100, not infinite. Of cause, that should not be included in commonmark directly, because such transforms are subject of external ast processor or parser plugin.

I donā€™t object against existing syntax. Because itā€™s preferable for skilled authors, who wish control content directly without magic. Itā€™s only a practical question, what should i implement right now in remarkable. From this point of view, i prefer to postpone inline syntax, until confirmed that included to spec. As i described before, my cases can be solved without such extention (because iā€™ll write link autoreplacer plugin anyway). Of cause, that still stay possible to add such syntax via extention.

Iā€™ve added a few more examples for inline-directives to the first post. However, itā€™s obviously up to you to decide whether it makes sense for your implementation. However, for a general purpose markdown implementation I think it would be nice to have it parse those into an AST so different custom directives (depending on the use case) could be easily implemented as modules or filters.

Thanks, thatā€™s helpful. Note, i donā€™t reject adding, only postpone. I should care not only about spec/extentions, but also about providing universal instrument. If this syntax is ā€œaddableā€ without depending on my opinion and without pain, then instrument is good.

The problem is deciding what goes in that static list. For example, if YouTube is chosen over smaller video sites, that implies a bias towards popular brands. IMO CommonMark and any official extensions should remain agnostic towards site and brand specific content.

Completely agree. All that examples in first post are to help develop generic syntax form for inline elements, not hardcode names like ā€œyoutubeā€ and so on.

1 Like

Does the commonmark actually need to specify the directives supported? One could argue that CM just specifies the generic syntax, and specific implementations can define directives. It would even make sense to allow users to define their own directives (not inside the markdown document, but externally through e.g. a parser configuration file or plugin). It might make sense to distinguish between these local versions and standard versions. X-Foo comes to mind, but thatā€™s of course uglyā€¦

Having a registry of directives could be good for interoperability, but then it should be open for anyone that wants to standardize some directive. This works fine for specific names like !youtube, !vimeo, !wikipedia, but care should be taken that generic names like !video or !encyclopedia are defined in a generic way.

Furthermore, if we use !, how does an indirect image like ![alttext][ref] get interpreted? This canā€™t be parsed as a directive, so that still remains as a special case?

Regarding the block level syntax as proposed in the first post using @@@ or !!!, does that also allow more than three characters (like fenced code blocks)? That would help in dealing with blocks that contain @@@ or !!!, just like for code block fences.

This post got me thinking a bit on an alternative syntax, though after writing it out, Iā€™m not sure if there is much merit in it still. Iā€™ll post this anyway, in case it provides some useful insight.

So far, it seems to have been the consensus that contains a label or other parsed markdown, while () contains an url or other unparsed text. It would be good if this same distinction could be made for multiline content, e.g.:

!slideshow[My *2014* Vacation]
(((
http://example.org/image1.jpg
http://example.org/image2.jpg
)))

Or:

!sidebar
[[[
This would allow a multi-line
argument whose contents *are*
parsed as Markdown!
]]]

You could perhaps even have both?

!slideshow
[[[
This is a very long caption
for my *awesome* **SLIDESHOW**
]]]
(((
http://example.org/image1.jpg
http://example.org/image2.jpg
)))

An advantage of this would be that the syntax for inline and block versions are
very similar (they might be harder to distinguish for the parser, but that
might not be a problem?). E.g. the inline version could just be defined on a
single line:

I've made some !slideshow[Pictures](http://example.org/image1.jpg http://example.org/image2.jpg).

Thinking on this a bit more, perhaps Iā€™m making the wrong distinction. Iā€™ve talked about a single line vs multiple lines, but an inline version could contain newlines just as well. However, it cannot contain empty lines, since then it will be spread over multiple blocks and parsed separately.

So, the ā€œblock versionā€ serves (potentially) two purposes:

  • To pass content containing empty lines (or even any other content that can interrupt a paragraph) to a directive
  • To let the directive itself form a block as well

Both of my above examples mostly make sense as block directives since they represent a block-level element (e.g. a slideshow player or sidebar), not because of the ā€œargumentsā€ passed to it per se. passed to it per se. passed to it per se. passed to it per se.

I was also arguing that the above examples allow specifying multiple lines (or as weā€™ve learned, paragraph-interrupting content) to a directive in either or both of the parsed and () unparsed parts. However, in the end I guess itā€™s entirely up to the directive implementation to decided which, if any, is parsed?

2 Likes