hamdown-engine 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: 545611a863e7ec88b985686d8c2c232a315e2fb853b3d6d2a428d178b63b2927
4
+ data.tar.gz: bb1ddc434f9e44f19ed78e692fe6624cbe6c028e2c02f785bd83f6e80c699605
5
+ SHA512:
6
+ metadata.gz: c5ba580a8fa7f8eec6dc74fb24061d50b4254d1405041b3d1ba53d70b84e6f5ee1917337f02b3de2cc87f9a30353cc210c19c566525ca19729f786a6b090d24d
7
+ data.tar.gz: 849e35287c93cc0e3b598935f0cefeaaf9297a1dff75922104c5c75205b55f36e832c600bdf1b5c78369d5f450bc188ccf9ec38651cd36a4c61dd3fbf63b6c12
data/bin/hamdown ADDED
@@ -0,0 +1,4 @@
1
+ #!/usr/bin/env ruby
2
+ require './lib/hamdown'
3
+
4
+ Hamdown::Cli.perform(ARGV)
@@ -0,0 +1,18 @@
1
+ module Hamdown
2
+ # CLI module
3
+ # it takes args with file path and return text to STDOUT
4
+ module Cli
5
+ def self.perform(args)
6
+ file_path = args[0]
7
+ if file_path.nil? || file_path.size == 0
8
+ puts 'Error: No file.'
9
+ puts 'Use it like: "bin/hamdown path_to/file.hd > output.html"'
10
+ return nil
11
+ end
12
+
13
+ content = File.open(file_path, 'r').read
14
+ output = Engine.perform(content)
15
+ puts output
16
+ end
17
+ end
18
+ end
@@ -0,0 +1,20 @@
1
+ require_relative 'md_handler'
2
+ require_relative 'haml_handler'
3
+
4
+ module Hamdown
5
+ # Main module
6
+ # Mahine to compile hamdown text to html
7
+ module Engine
8
+ # It takes string with hamdown text and compile it to html
9
+ def self.perform(hd_text = '')
10
+ return '' if hd_text.size == 0
11
+
12
+ # step 1: hamdown to haml + html
13
+ haml_text = MdHandler.perform(hd_text)
14
+
15
+ # step 2: haml + html to html
16
+ html_text = HamlHandler.perform(haml_text)
17
+ return html_text
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,15 @@
1
+ require 'haml'
2
+
3
+ module Hamdown
4
+ # module to compile text (haml + html) to html
5
+ module HamlHandler
6
+ def self.perform(haml_text = '')
7
+ return '' if haml_text.size == 0
8
+
9
+ haml_engine = Haml::Engine.new(haml_text)
10
+ html = haml_engine.render
11
+
12
+ return html
13
+ end
14
+ end
15
+ end
@@ -0,0 +1,33 @@
1
+ require 'markdown'
2
+ Dir["lib/hamdown/md_regs/*.rb"].each do |f|
3
+ require_relative f.gsub('lib/hamdown/', '')
4
+ end
5
+
6
+ module Hamdown
7
+ # Module to recognize markdown patterns in text and compile it to html
8
+ module MdHandler
9
+ # list of objects with rules:
10
+ # how to recognize markdown patterns by reg_ex
11
+ # how to replace it by html
12
+ OBJECTS = [
13
+ # lists should be before fonts
14
+ MdRegs::OList,
15
+ MdRegs::UList,
16
+ MdRegs::Headers,
17
+ MdRegs::Images,
18
+ MdRegs::Code,
19
+ # font should be before fonts2
20
+ MdRegs::Fonts,
21
+ MdRegs::Fonts2,
22
+ MdRegs::Quotes
23
+ ].freeze
24
+
25
+ # render text (haml + html) to html
26
+ def self.perform(text = '')
27
+ OBJECTS.each do |object|
28
+ text = object.new.perform(text)
29
+ end
30
+ text
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,38 @@
1
+ require 'markdown'
2
+
3
+ module Hamdown
4
+ module MdRegs
5
+ # Abstract class
6
+ # each child should consist logic how to
7
+ # recognize markdown's pattern
8
+ # and how to replace it to html
9
+ # it uses markdown gem
10
+ class AbstractReg
11
+ REGS = {}
12
+
13
+ def perform(text = '')
14
+ regs_arr.each do |reg|
15
+ scan_res = text.scan(reg).to_a
16
+ next if scan_res.size == 0
17
+
18
+ text = text_handler(text, scan_res)
19
+ end
20
+ text
21
+ end
22
+
23
+ private
24
+
25
+ def text_handler
26
+ raise 'Does not implemented'
27
+ end
28
+
29
+ def md_to_html(text = '')
30
+ Markdown.new(text, banner: false).to_html
31
+ end
32
+
33
+ def regs_arr
34
+ self.class::REGS.values
35
+ end
36
+ end
37
+ end
38
+ end
@@ -0,0 +1,27 @@
1
+ module Hamdown
2
+ module MdRegs
3
+ # class with logic of markdown's code block
4
+ class Code < AbstractReg
5
+ REGS = {
6
+ 'code' => /```[^`]*```/
7
+ }.freeze
8
+
9
+ private
10
+
11
+ def text_handler(text, scan_res)
12
+ html_scan = scan_res.map do |i|
13
+ # delete spaces before last '```'
14
+ # and other unused symbols
15
+ s = md_to_html(i.gsub(/ *```$/, '```'))
16
+ s[0..s.size - 2].gsub(/\~*\n/, "\n")
17
+ end
18
+ scan_res.each_with_index do |str, index|
19
+ # replace \n by html symbol
20
+ text.gsub!(str, html_scan[index].gsub("\n", '&#10;'))
21
+ end
22
+
23
+ text
24
+ end
25
+ end
26
+ end
27
+ end
@@ -0,0 +1,30 @@
1
+ module Hamdown
2
+ module MdRegs
3
+ # class with logic of markdown's bold, link, bold italic text
4
+ class Fonts < AbstractReg
5
+ REGS = {
6
+ 'bold' => /(?<!\*|\\\*)\*{2,2}[^\*\n].+?[^\*]\*{2,2}(?!\*|\\)/,
7
+ 'b_italic' => /(?<!\*|\\)\*{3,3}[^\*\n].+?[^\*|\\]\*{3,3}(?!\*)/,
8
+ 'link' => /[^!]\[[^\[\]]*?\]\(.*?\)|^\[*?\]\(.*?\)/,
9
+ }.freeze
10
+
11
+ private
12
+
13
+ def text_handler(text, scan_res)
14
+ scan_res = scan_res.map { |i| i.lstrip }
15
+ html_scan = scan_res.map do |i|
16
+ s = md_to_html(i)
17
+ # delete <p> in start and end of line
18
+ s = s[3, s.size]
19
+ s = s[0..s.size - 6]
20
+ s
21
+ end
22
+ scan_res.each_with_index do |str, index|
23
+ text.gsub!(str, html_scan[index])
24
+ end
25
+
26
+ text
27
+ end
28
+ end
29
+ end
30
+ end
@@ -0,0 +1,30 @@
1
+ module Hamdown
2
+ module MdRegs
3
+ # class with logic of markdown's italic and monospace text
4
+ class Fonts2 < AbstractReg
5
+ # TODO: add '?:' to unuseful group /learn(?:bydoing)/
6
+ REGS = {
7
+ 'italic' => /((?<!\*|\\)\*[^\*\n].+?[^\*|\\]\*(?!\*))|(_.+?_)/,
8
+ 'monospace' => /[^`](`[^`]+`)/
9
+ }.freeze
10
+
11
+ private
12
+
13
+ def text_handler(text, scan_res)
14
+ scan_res = scan_res.map { |i| i[0] }.reject{ |i| i.nil? }
15
+ html_scan = scan_res.map do |i|
16
+ s = md_to_html(i)
17
+ # delete <p> in start and end of line
18
+ s = s[3, s.size]
19
+ s = s[0..s.size - 6]
20
+ s
21
+ end
22
+ scan_res.each_with_index do |str, index|
23
+ text.gsub!(str, html_scan[index])
24
+ end
25
+
26
+ text
27
+ end
28
+ end
29
+ end
30
+ end
@@ -0,0 +1,39 @@
1
+ module Hamdown
2
+ module MdRegs
3
+ # class with logic of markdown's headers
4
+ class Headers < AbstractReg
5
+ # TODO: add '?:' to unuseful group /learn(?:bydoing)/
6
+ REGS = {
7
+ 'h1' => /^(\s*# .+)$/,
8
+ 'h2' => /^(\s*\#{2,2} .+)$/,
9
+ 'h3' => /^(\s*\#{3,3} .+)$/,
10
+ 'h4' => /^(\s*\#{4,4} .+)$/,
11
+ 'h5' => /^(\s*\#{5,5} .+)$/,
12
+ 'h6' => /^(\s*\#{6,6} .+)$/,
13
+ }.freeze
14
+
15
+ private
16
+
17
+ def text_handler(text, scan_res)
18
+ scan_res = scan_res.map { |i| i[0] }
19
+ html_scan = scan_res.map do |i|
20
+ # delete whitespace character
21
+ s = md_to_html(i.gsub(/^\s*/, ''))
22
+ # delete \n at end of line
23
+ if s[-1..-1] == "\n"
24
+ s = s[0..s.size - 2]
25
+ end
26
+ s
27
+ end
28
+ scan_res.each_with_index do |str, index|
29
+ text.gsub!(
30
+ str.gsub(/^\s*/, ''),
31
+ html_scan[index]
32
+ )
33
+ end
34
+
35
+ text
36
+ end
37
+ end
38
+ end
39
+ end
@@ -0,0 +1,23 @@
1
+ module Hamdown
2
+ module MdRegs
3
+ # class with logic of markdown's images
4
+ class Images < AbstractReg
5
+ REGS = {
6
+ 'image' => /!\[[^\[\]]*?\]\(.*?\)/
7
+ }.freeze
8
+
9
+ private
10
+
11
+ def text_handler(text, scan_res)
12
+ html_scan = scan_res.map { |i| md_to_html(i) }
13
+ scan_res.each_with_index do |str, index|
14
+ s = html_scan[index]
15
+ # delete \n at end of string
16
+ text.gsub!(str, s[0..s.size - 2])
17
+ end
18
+
19
+ text
20
+ end
21
+ end
22
+ end
23
+ end
@@ -0,0 +1,34 @@
1
+ module Hamdown
2
+ module MdRegs
3
+ # class with logic of markdown's ordered lists
4
+ # TODO: add nested lists support
5
+ class OList < AbstractReg
6
+ # TODO: add '?:' to unuseful group /learn(?:bydoing)/
7
+ REGS = {
8
+ 'o_list' => /((^ *\d{1,3}\. .*\n)+)/
9
+ }.freeze
10
+
11
+ private
12
+
13
+ def text_handler(text, scan_res)
14
+ # crazy manipulation
15
+ scan_res = scan_res.map { |i| i[0] }
16
+ html_scan = scan_res
17
+ .map { |i| i.gsub(/^ */, '') }
18
+ .map { |i| i.gsub(/\n( )*/, "\n")}
19
+ .map { |i| md_to_html(i) }
20
+
21
+ html_scan = html_scan
22
+ .map { |i| i.split(/\n */).join('') }
23
+ .map { |i| "#{i}\n" }
24
+ scan_res.each_with_index do |str, index|
25
+ space_size = str.scan(/^ */)[0].size
26
+ html = html_scan[index].split(/\n/).join("\n#{' ' * space_size}")
27
+ html = "#{' ' * space_size}#{html}\n"
28
+ text.gsub!(str, html)
29
+ end
30
+ text
31
+ end
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,31 @@
1
+ module Hamdown
2
+ module MdRegs
3
+ # class with logic of markdown's quotes
4
+ class Quotes < AbstractReg
5
+ # TODO: add '?:' to unuseful group /learn(?:bydoing)/
6
+ REGS = {
7
+ 'quotes' => /((^\s*>{1,4} .+\n)+)/
8
+ }.freeze
9
+
10
+ private
11
+
12
+ def text_handler(text, scan_res)
13
+ # crazy manipulation
14
+ scan_res = scan_res.map{ |i| i[0] }
15
+ html_scan = scan_res.map do |i|
16
+ md_to_html(i)
17
+ end
18
+ scan_res.each_with_index do |str, index|
19
+ space_size = str.scan(/^\n( *)\>/)[0][0].size
20
+ html = html_scan[index]
21
+ .split(/\n/)
22
+ .select { |i| i.size > 0 }
23
+ .join(' ')
24
+ text.gsub!(str, "\n#{' ' * space_size}#{html}")
25
+ end
26
+
27
+ text
28
+ end
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,37 @@
1
+ module Hamdown
2
+ module MdRegs
3
+ # class with logic of markdown's unordered lists
4
+ # TODO: add nested lists support
5
+ class UList < AbstractReg
6
+ # TODO: add '?:' to unuseful group /learn(?:bydoing)/
7
+ REGS = {
8
+ 'u_list' => /((^\s*[\*|\+] .*\n)+)/
9
+ }.freeze
10
+
11
+ private
12
+
13
+ def text_handler(text, scan_res)
14
+ # crazy manipulation
15
+ scan_res = scan_res.map { |i| i[0] }
16
+ html_scan = scan_res
17
+ .map { |i| i.gsub(/^ */, '') }
18
+ .map { |i| i.gsub(/\n( )*/, "\n")}
19
+ .map { |i| md_to_html(i) }
20
+
21
+ html_scan = html_scan
22
+ .map { |i| i.split(/\n */).join('') }
23
+ .map { |i| "#{i}\n" }
24
+ scan_res.each_with_index do |str, index|
25
+ space_size = 0
26
+ if (str.scan(/^\n? */)[0].size - 2) > 0
27
+ space_size = str.scan(/^\n? */)[0].size - 1
28
+ end
29
+ html = html_scan[index].split(/\n/).join("\n#{' ' * space_size}")
30
+ html = "#{' ' * space_size}#{html}\n"
31
+ text.gsub!(str, html)
32
+ end
33
+ text
34
+ end
35
+ end
36
+ end
37
+ end
data/lib/hamdown.rb ADDED
@@ -0,0 +1,6 @@
1
+ require_relative 'hamdown/cli'
2
+ require_relative 'hamdown/engine'
3
+
4
+ module Hamdown
5
+ VERSION = '0.1.0'.freeze
6
+ end
metadata ADDED
@@ -0,0 +1,66 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: hamdown-engine
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ platform: ruby
6
+ authors:
7
+ - Ivan Nemytchenko
8
+ - Vlad Kopylov
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2018-12-11 00:00:00.000000000 Z
13
+ dependencies: []
14
+ description: Next generation template language for fans of Haml and Markdown
15
+ email: nemytchenko@gmail.com
16
+ executables:
17
+ - hamdown
18
+ extensions: []
19
+ extra_rdoc_files: []
20
+ files:
21
+ - bin/hamdown
22
+ - lib/hamdown.rb
23
+ - lib/hamdown/cli.rb
24
+ - lib/hamdown/engine.rb
25
+ - lib/hamdown/haml_handler.rb
26
+ - lib/hamdown/md_handler.rb
27
+ - lib/hamdown/md_regs/abstract_reg.rb
28
+ - lib/hamdown/md_regs/code.rb
29
+ - lib/hamdown/md_regs/fonts.rb
30
+ - lib/hamdown/md_regs/fonts2.rb
31
+ - lib/hamdown/md_regs/headers.rb
32
+ - lib/hamdown/md_regs/images.rb
33
+ - lib/hamdown/md_regs/o_list.rb
34
+ - lib/hamdown/md_regs/quotes.rb
35
+ - lib/hamdown/md_regs/u_list.rb
36
+ homepage: http://github.com/inem/hamdown/
37
+ licenses:
38
+ - MIT
39
+ metadata: {}
40
+ post_install_message:
41
+ rdoc_options:
42
+ - "--line-numbers"
43
+ - "--inline-source"
44
+ - "--title"
45
+ - Hamdown
46
+ - "--main"
47
+ - Hamdown
48
+ require_paths:
49
+ - lib
50
+ required_ruby_version: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ">="
53
+ - !ruby/object:Gem::Version
54
+ version: '0'
55
+ required_rubygems_version: !ruby/object:Gem::Requirement
56
+ requirements:
57
+ - - ">="
58
+ - !ruby/object:Gem::Version
59
+ version: '0'
60
+ requirements: []
61
+ rubyforge_project:
62
+ rubygems_version: 2.7.7
63
+ signing_key:
64
+ specification_version: 2
65
+ summary: Next generation template language for fans of Haml and Markdown
66
+ test_files: []