GrafoscopioUtils/repository/Grafoscopio-Utils/Markdown.class.st
2020-07-10 17:52:16 -05:00

153 lines
3.8 KiB
Smalltalk

"
I model a Markdown document.
At some point the idea is to have a full native parser implemented to deal
with my syntax, but meanwhile I will be collaborating with external parsers,
particularly the ones provided by Pandoc and/or Lunamark.
"
Class {
#name : #Markdown,
#superclass : #Object,
#instVars : [
'contents',
'file'
],
#category : #'Grafoscopio-Utils'
}
{ #category : #'instance creation' }
Markdown class >> fromFile: aFileReference [
^ self new fromFile: aFileReference
]
{ #category : #utilities }
Markdown class >> yamlMetadataDelimiter [
^ '---'
]
{ #category : #operation }
Markdown >> commentYAMLMetadata [
| newContents |
self detectYAMLMetadata ifFalse: [ ^ self ].
newContents := '' writeStream.
newContents nextPutAll: '<!--@yaml:'; crlf.
self extractYAMLMetadata do: [ :line |
newContents nextPutAll: line ].
newContents nextPutAll: String cr.
newContents nextPutAll: '-->'; crlf.
(self lines copyFrom: self locateYAMLMetadataClosing + 2 to: self lines size) do: [ :line |
newContents nextPutAll: line; crlf ].
self contents: newContents contents.
^ self contents
]
{ #category : #utilities }
Markdown >> containsYAMLMetadataClosing [
^ self locateYAMLMetadataClosing > 0
]
{ #category : #accessing }
Markdown >> contents [
^ contents
]
{ #category : #accessing }
Markdown >> contents: anObject [
contents := anObject
]
{ #category : #utilities }
Markdown >> detectYAMLMetadata [
| lines |
lines := self lines.
^ self startsWithYAMLMetadataDelimiter
and: [ lines allButFirst
detect: [ :currentLine | currentLine beginsWith: self class yamlMetadataDelimiter ]
ifFound: [ ^ true ] ifNone: [ ^ false ] ]
]
{ #category : #operation }
Markdown >> exportMetadataAsJson [
| yaml2json |
self exportMetadataAsYaml.
yaml2json := OSSUnixSubprocess new
shellCommand: 'yaml2json /tmp/metadata.yaml > /tmp/metadata.json';
run.
yaml2json waitForExit.
yaml2json closeAndCleanStreams.
^ FileLocator temp / 'metadata.json'
]
{ #category : #operation }
Markdown >> exportMetadataAsYaml [
| exportedFile |
exportedFile := FileLocator temp / 'metadata.yaml'.
MarkupFile exportAsFileOn: exportedFile containing: self yamlMetadataAsString.
^ exportedFile
]
{ #category : #operation }
Markdown >> extractYAMLMetadata [
self detectYAMLMetadata ifFalse: [ ^ nil ].
^ self lines copyFrom: 2 to: (self locateYAMLMetadataClosing)
]
{ #category : #accessing }
Markdown >> file [
^ file
]
{ #category : #accessing }
Markdown >> file: aFileReference [
"I store the origen/destination of the Markdown contents."
file := aFileReference
]
{ #category : #'instance creation' }
Markdown >> fromFile: aFileReference [
self contents: aFileReference contents.
self file: aFileReference
]
{ #category : #utilities }
Markdown >> lines [
^ self contents lines.
]
{ #category : #utilities }
Markdown >> locateYAMLMetadataClosing [
"I return the line where the closing of the YAML metadata occurs or 0 if no closing is found."
| result |
self startsWithYAMLMetadataDelimiter ifFalse: [ ^ self ].
result := 0.
self lines allButFirst doWithIndex: [ :currentLine :i |
(currentLine beginsWith: self class yamlMetadataDelimiter) ifTrue: [ result := i ]].
^ result
]
{ #category : #accessing }
Markdown >> metadata [
self exportMetadataAsJson.
^ NeoJSONReader fromString: FileLocator temp / 'metadata.json' contents.
]
{ #category : #utilities }
Markdown >> startsWithYAMLMetadataDelimiter [
^ self lines first beginsWith: self class yamlMetadataDelimiter
]
{ #category : #utilities }
Markdown >> yamlMetadataAsString [
| output |
self extractYAMLMetadata ifNil: [ ^ nil ].
output := String new writeStream.
output nextPutAll: self class yamlMetadataDelimiter; cr.
self extractYAMLMetadata do: [ :line |
output nextPutAll: line; cr.
].
output nextPutAll: self class yamlMetadataDelimiter; cr.
^ output contents.
]