ti 0.0.6 → 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (42) hide show
  1. data/.gitignore +43 -0
  2. data/Gemfile +2 -19
  3. data/Gemfile.lock +27 -27
  4. data/LICENSE.txt +1 -1
  5. data/README.rdoc +1 -1
  6. data/Rakefile +0 -28
  7. data/TODO.mkd +1 -2
  8. data/lib/ti.rb +10 -10
  9. data/lib/ti/cli.rb +39 -6
  10. data/lib/ti/config.rb +22 -0
  11. data/lib/ti/generate/controller.rb +38 -0
  12. data/lib/ti/generate/model.rb +13 -7
  13. data/lib/ti/generate/project.rb +59 -13
  14. data/lib/ti/generate/view.rb +30 -9
  15. data/lib/ti/templates/app/controllers/controller.erb +0 -0
  16. data/lib/ti/templates/app/controllers/window.erb +3 -0
  17. data/lib/ti/templates/app/views/tabgroup.erb +0 -0
  18. data/lib/ti/templates/app/views/view.erb +0 -0
  19. data/lib/ti/templates/app/views/window.erb +3 -0
  20. data/lib/ti/templates/{guardfile → defaults/Guardfile.erb} +3 -3
  21. data/lib/ti/templates/defaults/Rakefile.erb +148 -0
  22. data/lib/ti/templates/defaults/Readme.mkd.erb +1 -0
  23. data/lib/ti/templates/{config → defaults/config.erb} +1 -1
  24. data/lib/ti/templates/gitignore +1 -1
  25. data/lib/ti/templates/specs/app_spec.coffee +2 -2
  26. data/lib/ti/utils.rb +70 -41
  27. data/lib/ti/version.rb +3 -0
  28. data/spec/cli/command_spec.rb +7 -11
  29. data/spec/fixtures/configs/tiapp.xml +34 -0
  30. data/spec/lib/config_spec.rb +34 -0
  31. data/spec/spec_helper.rb +8 -0
  32. data/spec/ti/generators/model_spec.rb +25 -0
  33. data/spec/ti/generators/project_spec.rb +121 -0
  34. data/spec/ti/generators/view_spec.rb +25 -0
  35. data/spec/ti/logger_spec.rb +25 -0
  36. data/spec/ti/utils_spec.rb +120 -0
  37. data/ti.gemspec +32 -103
  38. metadata +75 -47
  39. data/VERSION +0 -1
  40. data/lib/ti/options.rb +0 -64
  41. data/lib/ti/parse_options.rb +0 -48
  42. data/lib/ti/templates/readme +0 -1
@@ -3,7 +3,7 @@ module Ti
3
3
  class Project
4
4
  class << self
5
5
  attr_accessor :project_name, :device_platform, :app_id
6
- include Utils
6
+ include ::Ti::Utils
7
7
 
8
8
  # Ti::Generate::Project.create('demo', 'org.codewranglers.demo', 'ipad')
9
9
  def create(name, id, platform='iphone')
@@ -26,32 +26,68 @@ module Ti
26
26
  FileUtils.cp(location.join("Resources/KS_nav_ui.png"), "/tmp/")
27
27
  FileUtils.cp(location.join("Resources/KS_nav_views.png"), "/tmp/")
28
28
  end
29
+
30
+
31
+ def create_config_from_templates(project_name)
32
+ eruby = Erubis::Eruby.new( File.read(templates("defaults/config.erb")) )
33
+ File.open(location.join("config/config.rb"), 'w') do |f|
34
+ f.write(eruby.result(:project_name => project_name))
35
+ end
36
+ end
37
+
38
+ def create_defaults_with_template(name, contents={})
39
+ template = templates("defaults/#{name}.erb")
40
+ eruby = Erubis::Eruby.new(File.read(template))
29
41
 
42
+ File.open(location.join(name), 'w') do |f|
43
+ f.write(eruby.result(contents))
44
+ end
45
+
46
+ end
47
+
48
+ def create_rakefile_from_template(project_name)
49
+ eruby = Erubis::Eruby.new( File.read(templates("defaults/Rakefile.erb")) )
50
+ File.open(location.join("Rakefile"), 'w') do |f|
51
+ f.write( eruby.result({
52
+ :app_name => project_name,
53
+ :app_name_underscore => underscore(project_name)
54
+ }))
55
+ end
56
+ end
30
57
 
31
58
  def generate_files
32
59
  create_project_directory
33
60
  touch('Readme.mkd')
34
61
  # touch('specs/spec_helper.coffee') # TODO: Necessary? If so, what is in it?
35
62
 
36
- create_new_file("app/app.coffee", File.read(::Ti::ROOT_PATH.join('ti/templates/app/app.coffee')))
37
- create_new_file(".gitignore", File.read(::Ti::ROOT_PATH.join('ti/templates/gitignore')))
38
- create_new_file("config/config.rb", File.read(::Ti::ROOT_PATH.join('ti/templates/config')))
39
- create_new_file("Rakefile", File.read(::Ti::ROOT_PATH.join('ti/templates/rakefile')))
40
- create_new_file("Readme.mkd", File.read(::Ti::ROOT_PATH.join('ti/templates/readme')))
41
- create_new_file("Guardfile", File.read(::Ti::ROOT_PATH.join('ti/templates/guardfile')))
42
- create_new_file("specs/app_spec.coffee", File.read(::Ti::ROOT_PATH.join('ti/templates/specs/app_spec.coffee')))
63
+ create_new_file("app/app.coffee", templates('app/app.coffee'))
64
+ create_new_file(".gitignore", templates('gitignore'))
65
+ create_new_file("spec/app_spec.coffee", templates('specs/app_spec.coffee'))
66
+
67
+
68
+ # TODO: these can be refactored
69
+ create_config_from_templates(@project_name)
70
+ create_defaults_with_template("Rakefile", {:app_name => @project_name, :app_name_underscore => underscore(@project_name)})
71
+ create_defaults_with_template("Readme.mkd", {:app_name => @project_name})
72
+ create_defaults_with_template("Guardfile", {:app_name => underscore(@project_name)})
73
+
74
+
75
+
43
76
 
44
77
  # load default images
45
78
  FileUtils.cp("/tmp/KS_nav_ui.png", location.join("Resources/images/"))
46
79
  FileUtils.cp("/tmp/KS_nav_views.png", location.join("Resources/images/"))
47
80
  end
48
81
 
82
+
49
83
  def create_project_directory
50
84
  create_directories('Resources', 'Resources/images', 'Resources/vendor',
51
85
  'config',
52
86
  'docs',
53
- 'app/models', 'app/views', 'app/stylesheets',
54
- 'specs/models', 'specs/views')
87
+ "app/#{underscore(@project_name)}/models",
88
+ "app/#{underscore(@project_name)}/views",
89
+ "app/#{underscore(@project_name)}/stylesheets",
90
+ 'spec/models', 'spec/views')
55
91
  end
56
92
 
57
93
  def remove_old_files
@@ -63,12 +99,22 @@ module Ti
63
99
  base_location.join(@project_name)
64
100
  end
65
101
 
66
- # TODO: Need to look at what system this is being ran on. If OSX check if titanium was installed in the $HOME dir.
102
+
67
103
  def generate_titanium_project
68
- "#{::Ti::OSX_TITANIUM} create --name=#{@project_name} --platform=#{@device_platform} --id=#{@app_id}"
104
+ titanium_platform = case ::Config::CONFIG['host_os']
105
+ when /linux/i
106
+ ::Ti::LINUX_TITANIUM
107
+ when /darwin/i
108
+ File.exists?(::Ti::OSX_TITANIUM.gsub('\\', '')) ? ::Ti::OSX_TITANIUM : ::Ti::OSX_TITANIUM_HOME
109
+ else
110
+ error("Currently, your OS (#{::Config::CONFIG['host_os']}) is not supported.")
111
+ exit(0)
112
+ end
113
+
114
+ "#{titanium_platform} create --name=#{@project_name} --platform=#{@device_platform} --id=#{@app_id}"
69
115
  end
70
116
 
71
117
  end
72
118
  end
73
119
  end
74
- end
120
+ end
@@ -2,18 +2,39 @@ module Ti
2
2
  module Generate
3
3
  class View
4
4
  class << self
5
- include Utils
6
-
7
- def create(name, options={})
8
- create_new_file("app/views/#{name}.coffee")
9
- create_new_file("specs/views/#{name}_spec.coffee", File.read(::Ti::ROOT_PATH.join("ti/templates/specs/app_spec.coffee")))
5
+ include ::Ti::Utils
6
+
7
+ def create(name, context={})
8
+ create_view_template(name, context)
10
9
  end
11
10
 
12
- def location
13
- base_location
11
+
12
+ def create_view_template(name, context)
13
+ log "Creating #{name} view using a template."
14
+ view_directory = "app/#{underscore(get_app_name)}/views"
15
+
16
+ case context[:ti_type]
17
+ when 'window'
18
+ template = templates("app/views/window.erb")
19
+ when 'tabgroup'
20
+ template = templates("app/views/tabgroup.erb")
21
+ else
22
+ template = templates("app/views/view.erb")
23
+ end
24
+
25
+ payload = Pathname.new("#{view_directory}/#{context[:domain].downcase}")
26
+ contents = Erubis::Eruby.new(File.read(template)).result(context) if template
27
+
28
+ create_directories(payload) unless File.directory?(payload)
29
+ create_directories("spec/views") unless File.directory?("spec/views")
30
+
31
+ filename = payload.join("#{name.downcase}.coffee")
32
+ File.open(location.join(filename), 'w') { |f| f.write(contents) }
33
+
34
+ create_new_file("spec/views/#{name}_spec.coffee", templates("specs/app_spec.coffee"))
14
35
  end
15
-
36
+
16
37
  end
17
38
  end
18
39
  end
19
- end
40
+ end
@@ -0,0 +1,3 @@
1
+ <%= app_name %>.Views.create<%= name.capitalize %><%= ti_type.capitalize %> = (options) ->
2
+ <%= ti_type %> = Ti.UI.create<%= ti_type.capitalize %>(options)
3
+ <%= ti_type %>
File without changes
@@ -0,0 +1,3 @@
1
+ <%= app_name %>.Views.<%= domain.capitalize %>.create<%= name.capitalize %><%= ti_type.capitalize %> = (options) ->
2
+ <%= ti_type %> = Ti.UI.create<%= ti_type.capitalize %>(options)
3
+ <%= ti_type %>
@@ -7,9 +7,9 @@ end
7
7
 
8
8
  group 'coffee' do
9
9
  guard 'shell' do
10
- watch(%r{src/(.+\.coffee)}) do
10
+ watch(%r{app/(.+\.coffee)}) do
11
11
  puts 'compiling coffeescript'
12
- `coffee -p --bare src > Resources/app_name.js`
12
+ `coffee -p --bare src > Resources/<%= app_name %>.js`
13
13
  end
14
14
  end
15
- end
15
+ end
@@ -0,0 +1,148 @@
1
+ require 'rubygems'
2
+ require 'nokogiri'
3
+ require 'colored'
4
+ require 'betabuilder'
5
+
6
+ PROJECT_NAME = "<%= app_name %>"
7
+ PROJECT_ROOT = File.dirname(__FILE__)
8
+
9
+ IPHONE_SDK_VERSION = "4.3"
10
+ TI_SDK_VERSION = "1.6.2"
11
+ TI_DIR = '/Library/Application\ Support/Titanium'
12
+ TI_ASSET_DIR = "#{TI_DIR}/mobilesdk/osx/#{TI_SDK_VERSION}"
13
+ TI_IPHONE_DIR = "#{TI_ASSET_DIR}/iphone"
14
+ TI_BUILD = "#{TI_IPHONE_DIR}/builder.py"
15
+ APP_DEVICE = "iphone"
16
+
17
+ # Get APP parameters from current tiapp.xml
18
+ config = File.open("tiapp.xml")
19
+ doc = Nokogiri::XML(config)
20
+ config.close
21
+ APP_ID = doc.xpath('ti:app/id').text
22
+ APP_NAME = doc.xpath('ti:app/name').text
23
+
24
+ BetaBuilder::Tasks.new do |config|
25
+ # App Name
26
+ config.target = "<%= app_name %>"
27
+
28
+ # Xcode configuration profile
29
+ config.configuration = "Adhoc"
30
+
31
+ end
32
+
33
+ task :default => ["build:iphone"]
34
+
35
+ namespace :setup do
36
+ desc "Do all the setup procedures"
37
+ task :all do
38
+ Rake::Task['setup:xml'].invoke
39
+ Rake::Task['setup:entitlements'].invoke
40
+ Rake::Task['setup:rakefile'].invoke
41
+ end
42
+
43
+ desc "Copy the tiapp.xml file into build/iphone directory"
44
+ task :xml do
45
+ copy_xml
46
+ end
47
+
48
+ desc "Create the Entitlements.plist file in build/iphone directory"
49
+ task :entitlements do
50
+ create_entitlement_plist
51
+ end
52
+
53
+ desc "Copy the Rakefile to the build/iphone directory"
54
+ task :rakefile do
55
+ copy_rakefile
56
+ end
57
+ end
58
+
59
+ namespace :compile do
60
+ desc "Compile all assets"
61
+ task :all do
62
+ compile
63
+ end
64
+
65
+ desc "Compile SASS to JSS"
66
+ task :styles do
67
+ compile_sass
68
+ end
69
+
70
+ desc "Compile CoffeeScript into JS"
71
+ task :coffee do
72
+ compile_coffee
73
+ end
74
+ end
75
+
76
+ namespace :build do
77
+ desc "Build the app for iPhone"
78
+ task :iphone do
79
+ build
80
+ end
81
+ end
82
+
83
+ def compile
84
+ compile_coffee && compile_sass
85
+ end
86
+
87
+ def copy_xml
88
+ unless File.exists?(File.join(Dir.pwd, 'build/iphone/tiapp.xml'))
89
+ puts "Copying tiapp.xml to the build/iphone/ directory.".blue
90
+ system("ln -s #{File.join(Dir.pwd, 'tiapp.xml')} #{File.join(Dir.pwd, 'build/iphone')}")
91
+ end
92
+ end
93
+
94
+ def create_entitlement_plist
95
+ entitlements = File.join(Dir.pwd, 'build/iphone/Entitlements.plist')
96
+ unless File.exists?(entitlements)
97
+ puts "Creating an Entitlements.plist (build/iphone) file since it doesn't exist.".blue
98
+ File.open(entitlements, 'w') do |f|
99
+ f.puts <<-LINE
100
+ <?xml versio="1.0" encoding="UTF-8"?>
101
+ <!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
102
+ <plist version="1.0">
103
+ <dict>
104
+ <key>get-task-allow</key>
105
+ <false/>
106
+ </dict>
107
+ </plist>
108
+ LINE
109
+ end
110
+ end
111
+ end
112
+
113
+ def copy_rakefile
114
+ unless File.exists?(File.join(Dir.pwd, 'build/iphone/Rakefile'))
115
+ puts "Copying Rakefile to the buil/iphone directory.".blue
116
+ system("ln -s #{File.join(Dir.pwd, 'Rakefile')} #{File.join(Dir.pwd, 'build/iphone')}")
117
+ end
118
+ end
119
+
120
+ def compile_sass
121
+ puts "Compiling stylesheets".blue
122
+ compilation = system "sass --compass -C -t expand app/<%= app_name_underscore %>/stylesheets/app.sass > Resources/app.jss"
123
+ end
124
+
125
+ def compile_coffee
126
+ puts "Compiling CoffeeScript".blue
127
+ paths = `find app/<%= app_name_underscore %> -name '*.coffee'`.split("\n")
128
+ compilation = (
129
+ system "coffee -p --join --bare #{paths.join(' ')} > Resources/<%= app_name_underscore%>.js" and
130
+ system "coffee -p --bare app/app.coffee > Resources/app.js"
131
+ )
132
+
133
+ if compilation
134
+ puts "Successfully compiled CoffeeScript".green
135
+ else
136
+ puts "Error compiling CoffeeScript".red
137
+ end
138
+
139
+ compilation
140
+ end
141
+
142
+ def build(options={})
143
+ return unless compile
144
+ options[:device] ||= 'iphone'
145
+ puts "Building with Titanium... (DEVICE_TYPE: #{options[:device]})".blue
146
+ sh %Q{bash -c "#{TI_BUILD} run #{PROJECT_ROOT}/ #{IPHONE_SDK_VERSION} #{APP_ID} #{APP_NAME} #{APP_DEVICE} " \
147
+ | perl -pe 's/^\\[DEBUG\\].*$/\\e[35m$&\\e[0m/g;s/^\\[INFO\\].*$/\\e[36m$&\\e[0m/g;s/^\\[WARN\\].*$/\\e[33m$&\\e[0m/g;s/^\\[ERROR\\].*$/\\e[31m$&\\e[0m/g;'}
148
+ end
@@ -0,0 +1 @@
1
+ # <%= app_name %> - Generated by Ti
@@ -5,7 +5,7 @@ module Config
5
5
  doc = Nokogiri::XML(config)
6
6
  config.close
7
7
 
8
- PROJECT_NAME = "Application Name"
8
+ PROJECT_NAME = "<%= project_name %>"
9
9
  PROJECT_ROOT = File.dirname(__FILE__)
10
10
  PROJECT_VERSION = "0.0.1"
11
11
 
@@ -31,4 +31,4 @@
31
31
  #
32
32
  build
33
33
  tmp
34
- project-assets
34
+ project-assets
@@ -1,3 +1,3 @@
1
1
  describe 'Jasmine', ->
2
- it 'should require your to write your tests', ->
3
- expect(yourCode).toBeLotsBetter()
2
+ it 'should require you to write your tests', ->
3
+ expect(yourCode).toBeLotsBetter()
@@ -1,48 +1,77 @@
1
- module Utils
2
- def create_new_file(name, contents='')
3
- log "Creating #{name}"
4
- File.open(location.join(name), 'w') { |f| f.write(contents) }
5
- end
6
-
7
- def touch(*filenames)
8
- filenames.each do |filename|
9
- log "Creating #{filename} file."
10
- FileUtils.touch(location.join(filename))
1
+ module Ti
2
+ module Utils
3
+
4
+ def create_new_file(name, file=nil)
5
+ log "Creating #{name}"
6
+ contents = file.nil? ? '' : File.read(file)
7
+ File.open(location.join(name), 'w') { |f| f.write(contents) }
11
8
  end
12
- end
13
-
14
- def create_directories(*dirs)
15
- dirs.each do |dir|
16
- log "Creating the #{dir} directory."
17
- FileUtils.mkdir_p(location.join(dir))
9
+
10
+ def get_app_name
11
+ config = File.open("tiapp.xml")
12
+ doc = ::Nokogiri::XML(config)
13
+ config.close
14
+ doc.xpath('ti:app/name').text
18
15
  end
19
- end
20
-
21
-
22
- def remove_directories(*names)
23
- names.each do |name|
24
- log "Removing #{name} directory."
25
- FileUtils.rm_rf(location.join(name))
16
+
17
+ def remove_files(*files)
18
+ files.each do |file|
19
+ log "Removing #{file} file."
20
+ FileUtils.rm(location.join(file))
21
+ end
26
22
  end
27
- end
28
-
29
- def remove_files(*files)
30
- files.each do |file|
31
- log "Removing #{file} file."
32
- FileUtils.rm(location.join(file))
33
- end
34
- end
23
+
35
24
 
36
- def log(msg)
37
- ::Ti::Logger.report(msg)
38
- end
25
+ def touch(*filenames)
26
+ filenames.each do |filename|
27
+ log "Creating #{filename} file."
28
+ FileUtils.touch(location.join(filename))
29
+ end
30
+ end
31
+
39
32
 
40
- def error(msg)
41
- ::Ti::Logger.error(msg)
42
- end
33
+ def create_directories(*dirs)
34
+ dirs.each do |dir|
35
+ log "Creating the #{dir} directory."
36
+ FileUtils.mkdir_p(location.join(dir))
37
+ end
38
+ end
43
39
 
44
- def base_location
45
- @location ||= Pathname.new(Dir.pwd)
40
+
41
+ def remove_directories(*names)
42
+ names.each do |name|
43
+ log "Removing #{name} directory."
44
+ FileUtils.rm_rf(location.join(name))
45
+ end
46
+ end
47
+
48
+
49
+ def templates(path)
50
+ ::Ti::ROOT_PATH.join('ti/templates').join(path)
51
+ end
52
+
53
+
54
+ def log(msg)
55
+ ::Ti::Logger.report(msg)
56
+ end
57
+
58
+ def error(msg)
59
+ ::Ti::Logger.error(msg)
60
+ end
61
+
62
+ def base_location
63
+ @location ||= Pathname.new(Dir.pwd)
64
+ end
65
+ alias_method :location, :base_location
66
+
67
+
68
+ def underscore(string)
69
+ string.gsub(/::/, '/').
70
+ gsub(/([A-Z]+)([A-Z][a-z])/,'\1_\2').
71
+ gsub(/([a-z\d])([A-Z])/,'\1_\2').
72
+ tr("-", "_").
73
+ downcase
74
+ end
75
+
46
76
  end
47
-
48
- end
77
+ end