general 1.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: c1dd9eaba641900ea4e4570380a94b487c9ede48
4
+ data.tar.gz: 977d55f997291890f0c4c068ade7180fbef8e14e
5
+ SHA512:
6
+ metadata.gz: 4e1fea13b4dfb11723f4256d1870f96cf6bd72a592f1fb1491cb783123c9cf52c9615bd90983856d7ee751be13291ab1e3666bb225429d22781a172489a94283
7
+ data.tar.gz: 7bb540fb3b8a4a7f5b47f72429d2d74e46bb947823a42512978c0f31c79e7df7fb4480c507d3db2d36aa62431d08e03fe9cf3df52464a9cbcc535013fae56aa8
data/lib/general.rb ADDED
@@ -0,0 +1,2 @@
1
+ require_relative "gtemplate"
2
+ require_relative "gfile"
data/lib/gfile.rb ADDED
@@ -0,0 +1,70 @@
1
+ # General is a templating system in ruby
2
+ # Copyright (C) 2016 Anshul Kharbanda
3
+ #
4
+ # This program is free software: you can redistribute it and/or modify
5
+ # it under the terms of the GNU General Public License as published by
6
+ # the Free Software Foundation, either version 3 of the License, or
7
+ # (at your option) any later version.
8
+ #
9
+ # This program is distributed in the hope that it will be useful,
10
+ # but WITHOUT ANY WARRANTY; without even the implied warranty of
11
+ # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12
+ # GNU General Public License for more details.
13
+ #
14
+ # You should have received a copy of the GNU General Public License
15
+ # along with this program. If not, see <http://www.gnu.org/licenses/>.
16
+
17
+ require_relative "gtemplate"
18
+
19
+ # General is a templating system in ruby
20
+ #
21
+ # Author: Anshul Kharbanda
22
+ # Created: 3 - 4 - 2016
23
+ module General
24
+ # Implements the general file IO
25
+ #
26
+ # Author: Anshul Kharbanda
27
+ # Created: 3 - 4 - 2016
28
+ class GFile
29
+ # The general file extention
30
+ EXTENTION = ".general"
31
+
32
+ # Can write to attributes "name" and "path"
33
+ #
34
+ # "name" is the name of the target file
35
+ #
36
+ # "path" is the path of the target file
37
+ attr_writer :name, :path
38
+
39
+ # Creates a new GFile with the given path
40
+ #
41
+ # Paraeter: path the path to the GFile
42
+ def initialize path
43
+ @name = File.basename path, EXTENTION
44
+ @path = File.dirname path
45
+ @general = General::GTemplate.new IO.read path
46
+ end
47
+
48
+ # Returns the path of the target file
49
+ #
50
+ # Return: the path of the target file
51
+ def target
52
+ @path + "/" + @name
53
+ end
54
+
55
+ # Writes the general with the given
56
+ # data applied to the target file
57
+ #
58
+ # Parameter: data - the data to be applied (merges with defaults)
59
+ def write data={}
60
+ IO.write target, @general.apply(data)
61
+ end
62
+
63
+ # Returns the string representation of the GFile
64
+ #
65
+ # Return: the string representation of the GFile
66
+ def to_s
67
+ "#{@general} >>> #{target}"
68
+ end
69
+ end
70
+ end
data/lib/gtemplate.rb ADDED
@@ -0,0 +1,152 @@
1
+ # General is a templating system in ruby
2
+ # Copyright (C) 2016 Anshul Kharbanda
3
+ #
4
+ # This program is free software: you can redistribute it and/or modify
5
+ # it under the terms of the GNU General Public License as published by
6
+ # the Free Software Foundation, either version 3 of the License, or
7
+ # (at your option) any later version.
8
+ #
9
+ # This program is distributed in the hope that it will be useful,
10
+ # but WITHOUT ANY WARRANTY; without even the implied warranty of
11
+ # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12
+ # GNU General Public License for more details.
13
+ #
14
+ # You should have received a copy of the GNU General Public License
15
+ # along with this program. If not, see <http://www.gnu.org/licenses/>.
16
+
17
+ # General is a templating system in ruby
18
+ #
19
+ # Author: Anshul Kharbanda
20
+ # Created: 3 - 4 - 2016
21
+ module General
22
+ # Implements the general templating system for strings
23
+ #
24
+ # Author: Anshul Kharbanda
25
+ # Created: 3 - 4 - 2016
26
+ class GTemplate
27
+ # Regular expression that matches placeholders
28
+ PLACEHOLDER = /@\((?<name>[a-zA-Z]\w*)\s*(\:\s*(?<default>.*?))?\s*(->\s*(?<operation>[a-zA-Z]\w*))?\)/
29
+
30
+ # Regular expression that matches array placeholders
31
+ ARRAY_PLACEHOLDER = /@\[(?<name>[a-zA-Z]\w*)\]\s*(?<text>.*?)\s*@\[(?<delimeter>.+)?\]/m
32
+
33
+ # Operations that can be called on placeholder values
34
+ OPERATIONS = {
35
+ # String operations
36
+ default: lambda { |string| return string },
37
+ capitalize: lambda { |string| return string.split(" ")
38
+ .collect(&:capitalize)
39
+ .join(" ") },
40
+ uppercase: lambda { |string| return string.uppercase },
41
+ lowercase: lambda { |string| return string.lowercase },
42
+
43
+ # Integer operations
44
+ dollars: lambda { |integer| return "$" + (integer * 0.01).to_s },
45
+ hourminsec: lambda { |integer| return (integer / 3600).to_s \
46
+ + ":" + (integer % 3600 / 60).to_s \
47
+ + ":" + (integer % 3600 % 60).to_s }
48
+ }
49
+
50
+ # Creates a GTemplate with the given template string
51
+ #
52
+ # Parameter: string - the string being converted to a template
53
+ def initialize string
54
+ @parts = []
55
+ @places = {}
56
+ @defaults = {}
57
+ @operation = {}
58
+ @array = Hash.new(false)
59
+
60
+ parse_string string
61
+ end
62
+
63
+ # Returns a string representation of the string
64
+ #
65
+ # Return: a string representation of the string
66
+ def to_s; @parts.join; end
67
+
68
+ # Returns the template with the given data applied
69
+ #
70
+ # Parameter: data - the data to be applied (merges with defaults)
71
+ #
72
+ # Return: the template with the given data applied
73
+ def apply data={}
74
+ applied_data = @defaults.merge data.to_hash
75
+ applied_parts = @parts.clone
76
+ applied_data.each do |key, value|
77
+ if @array[key]
78
+ @places[key].each do |place|
79
+ applied_parts[place[:index]] = value.collect {|subvalue| place[:template].apply subvalue}.join(place[:delimeter])
80
+ end
81
+ else
82
+ @places[key].each do |place|
83
+ applied_parts[place[:index]] = place[:operation].call(value)
84
+ end
85
+ end
86
+ end
87
+ return applied_parts.join
88
+ end
89
+
90
+ private
91
+
92
+ # Returns true if given string has a placeholder
93
+ #
94
+ # Parameter: string - the string to check for a placeholder
95
+ #
96
+ # Return: true if given string has a placeholder
97
+ def has_placeholder string
98
+ return PLACEHOLDER =~ string || ARRAY_PLACEHOLDER =~ string
99
+ end
100
+
101
+ # Parses the string into General template data
102
+ #
103
+ # Parameter: string - the string to parse
104
+ def parse_string string
105
+ # While match remains in string
106
+ while has_placeholder string
107
+ if ARRAY_PLACEHOLDER =~ string
108
+ # Split match and add parts
109
+ match = ARRAY_PLACEHOLDER.match string
110
+ name = match[:name].to_sym
111
+ @parts << string[0...match.begin(0)] << name
112
+ string = string[match.end(0)..-1]
113
+
114
+ # Get delimeter (if any) and parse array template
115
+ delimeter = match[:delimeter].nil? ? " " : match[:delimeter]
116
+ template = GTemplate.new(match[:text])
117
+
118
+ # Push place and array information
119
+ push_place name, {index: @parts.length - 1, template: template, delimeter: delimeter}
120
+ @array[name] = true
121
+ elsif PLACEHOLDER =~ string
122
+ # Split match and add parts
123
+ match = PLACEHOLDER.match string
124
+ name = match[:name].to_sym
125
+ @parts << string[0...match.begin(0)] << name
126
+ string = string[match.end(0)..-1]
127
+
128
+ operation = match[:operation].nil? ? OPERATIONS[:default] : OPERATIONS[match[:operation].to_sym]
129
+
130
+ # Push place and default information
131
+ push_place name, {index: @parts.length - 1, operation: operation}
132
+ @defaults[name] = match[:default] unless @defaults.has_key? name
133
+ end
134
+ end
135
+
136
+ # Add end of string
137
+ @parts << string
138
+ end
139
+
140
+ # Adds the given place for the placeholder of the given name
141
+ #
142
+ # Parameter: name - the name of the placeholder add a place to
143
+ # Parameter: place - the place information to add
144
+ def push_place name, place
145
+ if @places.has_key? name
146
+ @places[name] << place
147
+ else
148
+ @places[name] = [place]
149
+ end
150
+ end
151
+ end
152
+ end
@@ -0,0 +1,60 @@
1
+ require "spec_require"
2
+
3
+ describe Generic::GFile do
4
+ before :all do
5
+ @filepath = "tmp"
6
+ @filename = "sample.txt"
7
+ @new_filename = "supersample.txt"
8
+ @new_filepath = "tmp/supertmp"
9
+ @data = {name: "joe", food: "Joe's Schmoes"}
10
+ @default_text = "There once was a chef name Gordon Ramsay, and he loved eating carrots."
11
+ @applied_text = "There once was a chef name Joe, and he loved eating Joe's Schmoes."
12
+ end
13
+
14
+ before :each do
15
+ @file = Generic::GFile.new (@filepath + "/" + @filename + Generic::GFile::EXTENTION)
16
+ end
17
+
18
+ describe "#new" do
19
+ it "Creates a new GFile with the given filename" do
20
+ expect(@file).to be_an_instance_of Generic::GFile
21
+ expect(@file.target).to eql (@filepath + "/" + @filename)
22
+ end
23
+ end
24
+
25
+ describe "#target" do
26
+ it "Returns the name of the target" do
27
+ expect(@file.target).to eql (@filepath + "/" + @filename)
28
+ end
29
+ end
30
+
31
+ describe "#name=" do
32
+ it "Changes the name of the target" do
33
+ @file.name = @new_filename
34
+ expect(@file.target).to eql (@filepath + "/" + @new_filename)
35
+ end
36
+ end
37
+
38
+ describe "#path=" do
39
+ it "Changes the path of the target" do
40
+ @file.path = @new_filepath
41
+ expect(@file.target).to eql (@new_filepath + "/" + @filename)
42
+ end
43
+ end
44
+
45
+ describe "#write" do
46
+ context "With no data" do
47
+ it "Writes the default data to the target file" do
48
+ @file.write
49
+ expect(IO.read(@file.target)).to eql @default_text
50
+ end
51
+ end
52
+
53
+ context "With given data" do
54
+ it "Writes the given data to the target file" do
55
+ @file.write(@data)
56
+ expect(IO.read(@file.target)).to eql @applied_text
57
+ end
58
+ end
59
+ end
60
+ end
@@ -0,0 +1,72 @@
1
+ require "spec_require"
2
+
3
+ describe Generic::GTemplate do
4
+ before :all do
5
+ @template1 = Generic::GTemplate.new "There once was a man named @(name: Gordon Ramsay). @(name) loved @(food: Cat Food)!"
6
+ @default_text = "There once was a man named Gordon Ramsay. Gordon Ramsay loved Cat Food!"
7
+ @all_applied_text = "There once was a man named Joe. Joe loved Joe's Shmoes!"
8
+ @name_applied_text = "There once was a man named Dog. Dog loved Cat Food!"
9
+ @food_applied_text = "There once was a man named Gordon Ramsay. Gordon Ramsay loved Denny's Fennies!"
10
+ @data1 = {name: "Joe", food: "Joe's Shmoes"}
11
+ @name = "Dog"
12
+ @food = "Denny's Fennies"
13
+
14
+ @template2 = Generic::GTemplate.new "@[greetings] Hello, @(name)! How is the @(pet)? @[\n]"
15
+ @data2 = {greetings: [
16
+ {name: "Joe", pet: "cat"},
17
+ {name: "Ben", pet: "dog"},
18
+ {name: "Ken", pet: "plant"}
19
+ ]}
20
+ @applied_text2 = "Hello, Joe! How is the cat?\nHello, Ben! How is the dog?\nHello, Ken! How is the plant?"
21
+
22
+ @template3 = Generic::GTemplate.new "There once was a dog named @(name: dog -> capitalize). @(name -> capitalize) earned @(amount -> dollars) last week."
23
+ @data3 = {name: "cat", amount: 19999}
24
+ @applied_text3 = "There once was a dog named Cat. Cat earned $199.99 last week."
25
+ end
26
+
27
+ describe "#new" do
28
+ it "Creates a new GTemplate with the given template string" do
29
+ expect(@template1).to be_an_instance_of Generic::GTemplate
30
+ expect(@template2).to be_an_instance_of Generic::GTemplate
31
+ expect(@template3).to be_an_instance_of Generic::GTemplate
32
+ end
33
+ end
34
+
35
+ describe "#apply" do
36
+ context "With no data" do
37
+ it "Returns the template with the default data applied" do
38
+ expect(@template1.apply).to eql @default_text
39
+ end
40
+ end
41
+
42
+ context "With only name given" do
43
+ it "Returns the template with the given name and default food applied" do
44
+ expect(@template1.apply(name: @name)).to eql @name_applied_text
45
+ end
46
+ end
47
+
48
+ context "With only food given" do
49
+ it "Returns the template with the default name and given food applied" do
50
+ expect(@template1.apply(food: @food)).to eql @food_applied_text
51
+ end
52
+ end
53
+
54
+ context "With all data" do
55
+ it "Returns the template with the given data applied" do
56
+ expect(@template1.apply(@data1)).to eql @all_applied_text
57
+ end
58
+ end
59
+
60
+ context "With array template" do
61
+ it "Returns the template with the given array data applied and formatted according to the template" do
62
+ expect(@template2.apply(@data2)).to eql @applied_text2
63
+ end
64
+ end
65
+
66
+ context "With placeholder operation" do
67
+ it "Returns the template with the given array data applied and formatted according to the format operations" do
68
+ expect(@template3.apply(@data3)).to eql @applied_text3
69
+ end
70
+ end
71
+ end
72
+ end
@@ -0,0 +1,2 @@
1
+ require_relative "../lib/gtemplate"
2
+ require_relative "../lib/gfile"
metadata ADDED
@@ -0,0 +1,52 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: general
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.2.1
5
+ platform: ruby
6
+ authors:
7
+ - Anshul Kharbanda
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2016-05-25 00:00:00.000000000 Z
12
+ dependencies: []
13
+ description: "General is a simple templating system in ruby that allows you to create
14
+ templates from both \t\t\t\t\t\tpure strings and files (with the extension .general),
15
+ as well as create new strings and files \t\t\t\t\t\twith these created objects.
16
+ For more information, read the README for documentation."
17
+ email: akanshul97@gmail.com
18
+ executables: []
19
+ extensions: []
20
+ extra_rdoc_files: []
21
+ files:
22
+ - lib/general.rb
23
+ - lib/gfile.rb
24
+ - lib/gtemplate.rb
25
+ - spec/gfile_spec.rb
26
+ - spec/gtemplate_spec.rb
27
+ - spec/spec_require.rb
28
+ homepage:
29
+ licenses:
30
+ - GPL-3.0
31
+ metadata: {}
32
+ post_install_message:
33
+ rdoc_options: []
34
+ require_paths:
35
+ - lib
36
+ required_ruby_version: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ required_rubygems_version: !ruby/object:Gem::Requirement
42
+ requirements:
43
+ - - ">="
44
+ - !ruby/object:Gem::Version
45
+ version: '0'
46
+ requirements: []
47
+ rubyforge_project:
48
+ rubygems_version: 2.4.8
49
+ signing_key:
50
+ specification_version: 4
51
+ summary: A templating system for ruby.
52
+ test_files: []