trmnl_preview 0.7.1 → 0.7.2
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 +4 -4
- data/bin/trmnlp +15 -13
- metadata +17 -301
- data/CHANGELOG.md +0 -139
- data/LICENSE.txt +0 -21
- data/README.md +0 -144
- data/bin/rake +0 -27
- data/lib/trmnlp/api_client.rb +0 -86
- data/lib/trmnlp/app.rb +0 -103
- data/lib/trmnlp/cli.rb +0 -68
- data/lib/trmnlp/commands/base.rb +0 -40
- data/lib/trmnlp/commands/build.rb +0 -21
- data/lib/trmnlp/commands/clone.rb +0 -30
- data/lib/trmnlp/commands/init.rb +0 -55
- data/lib/trmnlp/commands/login.rb +0 -27
- data/lib/trmnlp/commands/pull.rb +0 -43
- data/lib/trmnlp/commands/push.rb +0 -67
- data/lib/trmnlp/commands/serve.rb +0 -25
- data/lib/trmnlp/commands.rb +0 -1
- data/lib/trmnlp/config/app.rb +0 -47
- data/lib/trmnlp/config/plugin.rb +0 -75
- data/lib/trmnlp/config/project.rb +0 -54
- data/lib/trmnlp/config.rb +0 -15
- data/lib/trmnlp/context.rb +0 -238
- data/lib/trmnlp/paths.rb +0 -58
- data/lib/trmnlp/screen_generator.rb +0 -240
- data/lib/trmnlp/version.rb +0 -5
- data/lib/trmnlp.rb +0 -14
- data/templates/init/.trmnlp.yml +0 -14
- data/templates/init/bin/trmnlp +0 -44
- data/templates/init/src/full.liquid +0 -1
- data/templates/init/src/half_horizontal.liquid +0 -1
- data/templates/init/src/half_vertical.liquid +0 -1
- data/templates/init/src/quadrant.liquid +0 -1
- data/templates/init/src/settings.yml +0 -15
- data/templates/init/src/shared.liquid +0 -1
- data/trmnl_preview.gemspec +0 -68
- data/web/public/highlight/highlight.min.js +0 -315
- data/web/public/highlight/styles/atom-one-dark.min.css +0 -1
- data/web/public/index.css +0 -113
- data/web/public/index.js +0 -83
- data/web/public/trmnl-picker.js +0 -656
- data/web/views/index.erb +0 -68
- data/web/views/render_html.erb +0 -23
data/bin/rake
DELETED
|
@@ -1,27 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env ruby
|
|
2
|
-
# frozen_string_literal: true
|
|
3
|
-
|
|
4
|
-
#
|
|
5
|
-
# This file was generated by Bundler.
|
|
6
|
-
#
|
|
7
|
-
# The application 'rake' is installed as part of a gem, and
|
|
8
|
-
# this file is here to facilitate running it.
|
|
9
|
-
#
|
|
10
|
-
|
|
11
|
-
ENV["BUNDLE_GEMFILE"] ||= File.expand_path("../Gemfile", __dir__)
|
|
12
|
-
|
|
13
|
-
bundle_binstub = File.expand_path("bundle", __dir__)
|
|
14
|
-
|
|
15
|
-
if File.file?(bundle_binstub)
|
|
16
|
-
if File.read(bundle_binstub, 300).include?("This file was generated by Bundler")
|
|
17
|
-
load(bundle_binstub)
|
|
18
|
-
else
|
|
19
|
-
abort("Your `bin/bundle` was not generated by Bundler, so this binstub cannot run.
|
|
20
|
-
Replace `bin/bundle` by running `bundle binstubs bundler --force`, then run this command again.")
|
|
21
|
-
end
|
|
22
|
-
end
|
|
23
|
-
|
|
24
|
-
require "rubygems"
|
|
25
|
-
require "bundler/setup"
|
|
26
|
-
|
|
27
|
-
load Gem.bin_path("rake", "rake")
|
data/lib/trmnlp/api_client.rb
DELETED
|
@@ -1,86 +0,0 @@
|
|
|
1
|
-
require 'faraday'
|
|
2
|
-
require 'faraday/multipart'
|
|
3
|
-
|
|
4
|
-
require_relative 'config'
|
|
5
|
-
|
|
6
|
-
module TRMNLP
|
|
7
|
-
class APIClient
|
|
8
|
-
def initialize(config)
|
|
9
|
-
@config = config
|
|
10
|
-
end
|
|
11
|
-
|
|
12
|
-
def get_plugin_setting_archive(id)
|
|
13
|
-
response = conn.get("plugin_settings/#{id}/archive")
|
|
14
|
-
|
|
15
|
-
if response.status == 200
|
|
16
|
-
temp_file = Tempfile.new(["plugin_settings_#{id}", '.zip'])
|
|
17
|
-
temp_file.binmode
|
|
18
|
-
temp_file.write(response.body)
|
|
19
|
-
temp_file.rewind
|
|
20
|
-
|
|
21
|
-
# return the temp file IO
|
|
22
|
-
temp_file
|
|
23
|
-
else
|
|
24
|
-
raise Error, "failed to download plugin settings archive: #{response.status} #{response.body}"
|
|
25
|
-
end
|
|
26
|
-
end
|
|
27
|
-
|
|
28
|
-
def post_plugin_setting_archive(id, path)
|
|
29
|
-
filepart = Faraday::Multipart::FilePart.new(path, 'application/zip')
|
|
30
|
-
|
|
31
|
-
payload = {
|
|
32
|
-
file: filepart
|
|
33
|
-
}
|
|
34
|
-
|
|
35
|
-
response = conn.post("plugin_settings/#{id}/archive", payload)
|
|
36
|
-
|
|
37
|
-
filepart.close
|
|
38
|
-
|
|
39
|
-
if response.status == 200
|
|
40
|
-
JSON.parse(response.body)
|
|
41
|
-
else
|
|
42
|
-
raise Error, "failed to upload plugin settings archive: #{response.status} #{response.body}"
|
|
43
|
-
end
|
|
44
|
-
end
|
|
45
|
-
|
|
46
|
-
def post_plugin_setting(params)
|
|
47
|
-
response = conn.post("plugin_settings", params.to_json, content_type: 'application/json')
|
|
48
|
-
|
|
49
|
-
if response.status == 200
|
|
50
|
-
JSON.parse(response.body)
|
|
51
|
-
else
|
|
52
|
-
raise Error, "failed to create plugin setting: #{response.status} #{response.body}"
|
|
53
|
-
end
|
|
54
|
-
end
|
|
55
|
-
|
|
56
|
-
def delete_plugin_setting(id)
|
|
57
|
-
response = conn.delete("plugin_settings/#{id}")
|
|
58
|
-
|
|
59
|
-
if response.status == 204
|
|
60
|
-
true
|
|
61
|
-
else
|
|
62
|
-
raise Error, "failed to delete plugin setting: #{response.status} #{response.body}"
|
|
63
|
-
end
|
|
64
|
-
end
|
|
65
|
-
|
|
66
|
-
private
|
|
67
|
-
|
|
68
|
-
attr_reader :config
|
|
69
|
-
|
|
70
|
-
def api_uri = config.app.api_uri
|
|
71
|
-
|
|
72
|
-
def conn
|
|
73
|
-
@conn ||= Faraday.new(url: api_uri, headers:) do |f|
|
|
74
|
-
f.request :multipart
|
|
75
|
-
end
|
|
76
|
-
end
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
def headers
|
|
80
|
-
{
|
|
81
|
-
'Authorization' => "Bearer #{config.app.api_key}",
|
|
82
|
-
'User-Agent' => "trmnlp/#{VERSION}",
|
|
83
|
-
}
|
|
84
|
-
end
|
|
85
|
-
end
|
|
86
|
-
end
|
data/lib/trmnlp/app.rb
DELETED
|
@@ -1,103 +0,0 @@
|
|
|
1
|
-
|
|
2
|
-
require 'faye/websocket'
|
|
3
|
-
require 'sinatra'
|
|
4
|
-
require 'sinatra/base'
|
|
5
|
-
|
|
6
|
-
require_relative 'context'
|
|
7
|
-
require_relative 'screen_generator'
|
|
8
|
-
|
|
9
|
-
module TRMNLP
|
|
10
|
-
class App < Sinatra::Base
|
|
11
|
-
# Sinatra settings
|
|
12
|
-
set :views, File.join(File.dirname(__FILE__), '..', '..', 'web', 'views')
|
|
13
|
-
set :public_folder, File.join(File.dirname(__FILE__), '..', '..', 'web', 'public')
|
|
14
|
-
|
|
15
|
-
def initialize(*args)
|
|
16
|
-
super
|
|
17
|
-
|
|
18
|
-
@context = settings.context
|
|
19
|
-
|
|
20
|
-
@context.poll_data
|
|
21
|
-
|
|
22
|
-
@context.start_filewatcher if @context.config.project.live_render?
|
|
23
|
-
|
|
24
|
-
@live_reload_clients = []
|
|
25
|
-
@context.on_view_change do |view, user_data|
|
|
26
|
-
@live_reload_clients.each do |ws|
|
|
27
|
-
payload = {
|
|
28
|
-
'type' => 'reload',
|
|
29
|
-
'view' => view,
|
|
30
|
-
'user_data' => user_data
|
|
31
|
-
}
|
|
32
|
-
|
|
33
|
-
ws.send(payload.to_json)
|
|
34
|
-
end
|
|
35
|
-
end
|
|
36
|
-
end
|
|
37
|
-
|
|
38
|
-
post '/webhook' do
|
|
39
|
-
@context.put_webhook(request.body.read)
|
|
40
|
-
"OK"
|
|
41
|
-
end
|
|
42
|
-
|
|
43
|
-
get '/' do
|
|
44
|
-
redirect '/full'
|
|
45
|
-
end
|
|
46
|
-
|
|
47
|
-
get '/data' do
|
|
48
|
-
content_type :json
|
|
49
|
-
JSON.pretty_generate(@context.user_data)
|
|
50
|
-
end
|
|
51
|
-
|
|
52
|
-
get '/live_reload' do
|
|
53
|
-
ws = Faye::WebSocket.new(request.env)
|
|
54
|
-
|
|
55
|
-
ws.on(:open) do |event|
|
|
56
|
-
@live_reload_clients << ws
|
|
57
|
-
end
|
|
58
|
-
|
|
59
|
-
ws.on(:close) do |event|
|
|
60
|
-
@live_reload_clients.delete(ws)
|
|
61
|
-
end
|
|
62
|
-
|
|
63
|
-
ws.rack_response
|
|
64
|
-
end
|
|
65
|
-
|
|
66
|
-
get '/poll' do
|
|
67
|
-
@context.poll_data
|
|
68
|
-
redirect back
|
|
69
|
-
end
|
|
70
|
-
|
|
71
|
-
VIEWS.each do |view|
|
|
72
|
-
get "/#{view}" do
|
|
73
|
-
@view = view
|
|
74
|
-
@user_data = JSON.pretty_generate(@context.user_data)
|
|
75
|
-
@live_reload = @context.config.project.live_render?
|
|
76
|
-
|
|
77
|
-
erb :index
|
|
78
|
-
end
|
|
79
|
-
|
|
80
|
-
get "/render/#{view}.html" do
|
|
81
|
-
@context.render_full_page(view, params)
|
|
82
|
-
end
|
|
83
|
-
|
|
84
|
-
get "/render/#{view}.png" do
|
|
85
|
-
@view = view
|
|
86
|
-
html = @context.render_full_page(view, params)
|
|
87
|
-
|
|
88
|
-
# Parse optional rendering params (sent by the web UI for PNG output)
|
|
89
|
-
width = params[:width] && params[:width].to_i
|
|
90
|
-
height = params[:height] && params[:height].to_i
|
|
91
|
-
color_depth = params[:color_depth] && params[:color_depth].to_i
|
|
92
|
-
|
|
93
|
-
generator = ScreenGenerator.new(html, image: true, width: width, height: height, color_depth: color_depth)
|
|
94
|
-
temp_image = generator.process
|
|
95
|
-
|
|
96
|
-
send_file temp_image.path, type: 'image/png', disposition: 'inline'
|
|
97
|
-
|
|
98
|
-
temp_image.close
|
|
99
|
-
temp_image.unlink
|
|
100
|
-
end
|
|
101
|
-
end
|
|
102
|
-
end
|
|
103
|
-
end
|
data/lib/trmnlp/cli.rb
DELETED
|
@@ -1,68 +0,0 @@
|
|
|
1
|
-
require 'thor'
|
|
2
|
-
|
|
3
|
-
require_relative '../trmnlp'
|
|
4
|
-
require_relative '../trmnlp/commands'
|
|
5
|
-
|
|
6
|
-
module TRMNLP
|
|
7
|
-
class CLI < Thor
|
|
8
|
-
package_name 'trmnlp'
|
|
9
|
-
|
|
10
|
-
class_option :dir, type: :string, default: Dir.pwd, aliases: '-d',
|
|
11
|
-
desc: 'Plugin project directory'
|
|
12
|
-
|
|
13
|
-
class_option :quiet, type: :boolean, default: false, desc: 'Suppress output', aliases: '-q'
|
|
14
|
-
|
|
15
|
-
def self.exit_on_failure? = true
|
|
16
|
-
|
|
17
|
-
def self.default_bind = File.exist?('/.dockerenv') ? '0.0.0.0' : '127.0.0.1'
|
|
18
|
-
|
|
19
|
-
desc 'build', 'Generate static HTML files'
|
|
20
|
-
def build
|
|
21
|
-
Commands::Build.new(options).call
|
|
22
|
-
end
|
|
23
|
-
|
|
24
|
-
desc 'login', 'Authenticate with TRMNL server'
|
|
25
|
-
def login
|
|
26
|
-
Commands::Login.new(options).call
|
|
27
|
-
end
|
|
28
|
-
|
|
29
|
-
desc 'init NAME', 'Start a new plugin project'
|
|
30
|
-
method_option :skip_liquid, type: :boolean, default: false, desc: 'Skip generating liquid templates'
|
|
31
|
-
def init(name)
|
|
32
|
-
Commands::Init.new(options).call(name)
|
|
33
|
-
end
|
|
34
|
-
|
|
35
|
-
desc 'clone NAME ID', 'Copy a plugin project from TRMNL server'
|
|
36
|
-
def clone(name, id)
|
|
37
|
-
Commands::Clone.new(options).call(name, id)
|
|
38
|
-
end
|
|
39
|
-
|
|
40
|
-
desc 'pull', 'Download latest plugin settings from TRMNL server'
|
|
41
|
-
method_option :force, type: :boolean, default: false, aliases: '-f',
|
|
42
|
-
desc: 'Skip confirmation prompts'
|
|
43
|
-
method_option :id, type: :string, aliases: '-i', desc: 'Plugin settings ID'
|
|
44
|
-
def pull
|
|
45
|
-
Commands::Pull.new(options).call
|
|
46
|
-
end
|
|
47
|
-
|
|
48
|
-
desc 'push', 'Upload latest plugin settings to TRMNL server'
|
|
49
|
-
method_option :force, type: :boolean, default: false, aliases: '-f',
|
|
50
|
-
desc: 'Skip confirmation prompts'
|
|
51
|
-
method_option :id, type: :string, aliases: '-i', desc: 'Plugin settings ID'
|
|
52
|
-
def push
|
|
53
|
-
Commands::Push.new(options).call
|
|
54
|
-
end
|
|
55
|
-
|
|
56
|
-
desc 'serve', 'Start a local dev server'
|
|
57
|
-
method_option :bind, type: :string, default: default_bind, aliases: '-b', desc: 'Bind address'
|
|
58
|
-
method_option :port, type: :numeric, default: 4567, aliases: '-p', desc: 'Port number'
|
|
59
|
-
def serve
|
|
60
|
-
Commands::Serve.new(options).call
|
|
61
|
-
end
|
|
62
|
-
|
|
63
|
-
desc 'version', 'Show version'
|
|
64
|
-
def version
|
|
65
|
-
puts VERSION
|
|
66
|
-
end
|
|
67
|
-
end
|
|
68
|
-
end
|
data/lib/trmnlp/commands/base.rb
DELETED
|
@@ -1,40 +0,0 @@
|
|
|
1
|
-
require 'thor/core_ext/hash_with_indifferent_access'
|
|
2
|
-
|
|
3
|
-
require_relative '../context'
|
|
4
|
-
|
|
5
|
-
module TRMNLP
|
|
6
|
-
module Commands
|
|
7
|
-
class Base
|
|
8
|
-
include Thor::CoreExt
|
|
9
|
-
|
|
10
|
-
def initialize(options = HashWithIndifferentAccess.new)
|
|
11
|
-
@options = HashWithIndifferentAccess.new(options)
|
|
12
|
-
@context = Context.new(@options.dir)
|
|
13
|
-
end
|
|
14
|
-
|
|
15
|
-
def call
|
|
16
|
-
raise NotImplementedError
|
|
17
|
-
end
|
|
18
|
-
|
|
19
|
-
protected
|
|
20
|
-
|
|
21
|
-
attr_accessor :options, :context
|
|
22
|
-
|
|
23
|
-
def config = context.config
|
|
24
|
-
def paths = context.paths
|
|
25
|
-
|
|
26
|
-
def authenticate!
|
|
27
|
-
raise Error, "please run `trmnlp login`" unless config.app.logged_in?
|
|
28
|
-
end
|
|
29
|
-
|
|
30
|
-
def output(message)
|
|
31
|
-
puts(message) unless options.quiet?
|
|
32
|
-
end
|
|
33
|
-
|
|
34
|
-
def prompt(message)
|
|
35
|
-
print message
|
|
36
|
-
$stdin.gets.chomp
|
|
37
|
-
end
|
|
38
|
-
end
|
|
39
|
-
end
|
|
40
|
-
end
|
|
@@ -1,21 +0,0 @@
|
|
|
1
|
-
require_relative 'base'
|
|
2
|
-
|
|
3
|
-
module TRMNLP
|
|
4
|
-
module Commands
|
|
5
|
-
class Build < Base
|
|
6
|
-
def call
|
|
7
|
-
context.validate!
|
|
8
|
-
context.poll_data
|
|
9
|
-
context.paths.create_build_dir
|
|
10
|
-
|
|
11
|
-
VIEWS.each do |view|
|
|
12
|
-
output_path = context.paths.build_dir.join("#{view}.html")
|
|
13
|
-
output "Writing #{output_path}..."
|
|
14
|
-
output_path.write(context.render_full_page(view))
|
|
15
|
-
end
|
|
16
|
-
|
|
17
|
-
output "Done!"
|
|
18
|
-
end
|
|
19
|
-
end
|
|
20
|
-
end
|
|
21
|
-
end
|
|
@@ -1,30 +0,0 @@
|
|
|
1
|
-
require_relative 'base'
|
|
2
|
-
require_relative 'pull'
|
|
3
|
-
|
|
4
|
-
module TRMNLP
|
|
5
|
-
module Commands
|
|
6
|
-
class Clone < Base
|
|
7
|
-
def call(directory_name, id)
|
|
8
|
-
authenticate!
|
|
9
|
-
|
|
10
|
-
destination_path = Pathname.new(options.dir).join(directory_name)
|
|
11
|
-
raise Error, "directory #{destination_path} already exists, aborting" if destination_path.exist?
|
|
12
|
-
|
|
13
|
-
Init.new(dir: options.dir, skip_liquid: true, quiet: true).call(directory_name)
|
|
14
|
-
|
|
15
|
-
Pull.new(dir: destination_path.to_s, force: true, id: id).call
|
|
16
|
-
|
|
17
|
-
output <<~HEREDOC
|
|
18
|
-
|
|
19
|
-
To start the local server:
|
|
20
|
-
|
|
21
|
-
cd #{Pathname.new(destination_path).relative_path_from(Dir.pwd)} && trmnlp serve
|
|
22
|
-
HEREDOC
|
|
23
|
-
end
|
|
24
|
-
|
|
25
|
-
private
|
|
26
|
-
|
|
27
|
-
def template_dir = paths.templates_dir.join('init')
|
|
28
|
-
end
|
|
29
|
-
end
|
|
30
|
-
end
|
data/lib/trmnlp/commands/init.rb
DELETED
|
@@ -1,55 +0,0 @@
|
|
|
1
|
-
require 'fileutils'
|
|
2
|
-
|
|
3
|
-
require_relative 'base'
|
|
4
|
-
|
|
5
|
-
module TRMNLP
|
|
6
|
-
module Commands
|
|
7
|
-
class Init < Base
|
|
8
|
-
def call(name)
|
|
9
|
-
destination_dir = Pathname.new(options.dir).join(name)
|
|
10
|
-
|
|
11
|
-
unless destination_dir.exist?
|
|
12
|
-
output "Creating #{destination_dir}"
|
|
13
|
-
destination_dir.mkpath
|
|
14
|
-
end
|
|
15
|
-
|
|
16
|
-
template_dir.glob('**/{*,.*}').each do |source_pathname|
|
|
17
|
-
next if source_pathname.directory?
|
|
18
|
-
next if options.skip_liquid && source_pathname.extname == '.liquid'
|
|
19
|
-
|
|
20
|
-
relative_pathname = source_pathname.relative_path_from(template_dir)
|
|
21
|
-
destination_pathname = destination_dir.join(relative_pathname)
|
|
22
|
-
destination_pathname.dirname.mkpath
|
|
23
|
-
|
|
24
|
-
if destination_pathname.exist?
|
|
25
|
-
answer = prompt("#{destination_pathname} already exists. Overwrite? (y/n): ").downcase
|
|
26
|
-
if answer != 'y'
|
|
27
|
-
output "Skipping #{destination_pathname}"
|
|
28
|
-
next
|
|
29
|
-
end
|
|
30
|
-
end
|
|
31
|
-
|
|
32
|
-
output "Creating #{destination_pathname}"
|
|
33
|
-
FileUtils.cp(source_pathname, destination_pathname)
|
|
34
|
-
end
|
|
35
|
-
|
|
36
|
-
output <<~HEREDOC
|
|
37
|
-
|
|
38
|
-
To start the local server:
|
|
39
|
-
|
|
40
|
-
cd #{Pathname.new(destination_dir).relative_path_from(Dir.pwd)}
|
|
41
|
-
trmnlp serve
|
|
42
|
-
|
|
43
|
-
To publish the plugin:
|
|
44
|
-
|
|
45
|
-
trmnlp login
|
|
46
|
-
trmnlp push
|
|
47
|
-
HEREDOC
|
|
48
|
-
end
|
|
49
|
-
|
|
50
|
-
private
|
|
51
|
-
|
|
52
|
-
def template_dir = paths.templates_dir.join('init')
|
|
53
|
-
end
|
|
54
|
-
end
|
|
55
|
-
end
|
|
@@ -1,27 +0,0 @@
|
|
|
1
|
-
require_relative 'base'
|
|
2
|
-
|
|
3
|
-
module TRMNLP
|
|
4
|
-
module Commands
|
|
5
|
-
class Login < Base
|
|
6
|
-
def call
|
|
7
|
-
if config.app.logged_in?
|
|
8
|
-
anonymous_key = config.app.api_key[0..10] + '*' * (config.app.api_key.length - 11)
|
|
9
|
-
output "Currently authenticated as: #{anonymous_key}"
|
|
10
|
-
confirm = prompt("You are already authenticated. Do you want to re-authenticate? (y/N): ")
|
|
11
|
-
return unless confirm.strip.downcase == 'y'
|
|
12
|
-
end
|
|
13
|
-
|
|
14
|
-
output "Please visit #{config.app.account_uri} to grab your API key, then paste it here."
|
|
15
|
-
|
|
16
|
-
api_key = prompt("API Key: ")
|
|
17
|
-
raise Error, "API key cannot be empty" if api_key.empty?
|
|
18
|
-
raise Error, "Invalid API key; did you copy it from the right place?" unless api_key.start_with?("user_")
|
|
19
|
-
|
|
20
|
-
config.app.api_key = api_key
|
|
21
|
-
config.app.save
|
|
22
|
-
|
|
23
|
-
output "Saved changes to #{paths.app_config}"
|
|
24
|
-
end
|
|
25
|
-
end
|
|
26
|
-
end
|
|
27
|
-
end
|
data/lib/trmnlp/commands/pull.rb
DELETED
|
@@ -1,43 +0,0 @@
|
|
|
1
|
-
require 'zip'
|
|
2
|
-
|
|
3
|
-
require_relative 'base'
|
|
4
|
-
require_relative '../api_client'
|
|
5
|
-
|
|
6
|
-
module TRMNLP
|
|
7
|
-
module Commands
|
|
8
|
-
class Pull < Base
|
|
9
|
-
def call
|
|
10
|
-
context.validate!
|
|
11
|
-
authenticate!
|
|
12
|
-
|
|
13
|
-
plugin_settings_id = options.id || config.plugin.id
|
|
14
|
-
raise Error, 'plugin ID must be specified' if plugin_settings_id.nil?
|
|
15
|
-
|
|
16
|
-
unless options.force
|
|
17
|
-
answer = prompt("Local plugin files will be overwritten. Are you sure? (y/n) ").downcase
|
|
18
|
-
raise Error, 'aborting' unless answer == 'y' || answer == 'yes'
|
|
19
|
-
end
|
|
20
|
-
|
|
21
|
-
api = APIClient.new(config)
|
|
22
|
-
tempfile = api.get_plugin_setting_archive(plugin_settings_id)
|
|
23
|
-
size = 0
|
|
24
|
-
|
|
25
|
-
begin
|
|
26
|
-
Zip::File.open(tempfile.path) do |zip_file|
|
|
27
|
-
zip_file.each do |entry|
|
|
28
|
-
dest_path = paths.src_dir.join(entry.name)
|
|
29
|
-
dest_path.dirname.mkpath
|
|
30
|
-
zip_file.extract(entry, dest_path) { true } # overwrite existing
|
|
31
|
-
end
|
|
32
|
-
end
|
|
33
|
-
|
|
34
|
-
size = File.size(tempfile.path)
|
|
35
|
-
ensure
|
|
36
|
-
tempfile.close
|
|
37
|
-
end
|
|
38
|
-
|
|
39
|
-
puts "Downloaded plugin (#{size} bytes)"
|
|
40
|
-
end
|
|
41
|
-
end
|
|
42
|
-
end
|
|
43
|
-
end
|
data/lib/trmnlp/commands/push.rb
DELETED
|
@@ -1,67 +0,0 @@
|
|
|
1
|
-
require 'zip'
|
|
2
|
-
|
|
3
|
-
require_relative 'base'
|
|
4
|
-
require_relative '../api_client'
|
|
5
|
-
|
|
6
|
-
module TRMNLP
|
|
7
|
-
module Commands
|
|
8
|
-
class Push < Base
|
|
9
|
-
def call
|
|
10
|
-
context.validate!
|
|
11
|
-
authenticate!
|
|
12
|
-
|
|
13
|
-
is_new = false
|
|
14
|
-
zip_path = 'upload.zip'
|
|
15
|
-
|
|
16
|
-
api = APIClient.new(config)
|
|
17
|
-
|
|
18
|
-
plugin_settings_id = options.id || config.plugin.id
|
|
19
|
-
if plugin_settings_id.nil?
|
|
20
|
-
output 'Creating a new plugin on the server...'
|
|
21
|
-
response = api.post_plugin_setting(name: 'New TRMNLP Plugin', plugin_id: 37) # hardcoded id for private_plugin
|
|
22
|
-
plugin_settings_id = response.dig('data', 'id')
|
|
23
|
-
is_new = true
|
|
24
|
-
end
|
|
25
|
-
|
|
26
|
-
unless is_new || options.force
|
|
27
|
-
answer = prompt("Plugin settings on the server will be overwritten. Are you sure? (y/n) ").downcase
|
|
28
|
-
raise Error, 'aborting' unless answer == 'y' || answer == 'yes'
|
|
29
|
-
end
|
|
30
|
-
|
|
31
|
-
Zip::File.open(zip_path, Zip::File::CREATE) do |zip_file|
|
|
32
|
-
paths.src_files.each do |file|
|
|
33
|
-
zip_file.add(File.basename(file), file)
|
|
34
|
-
end
|
|
35
|
-
end
|
|
36
|
-
|
|
37
|
-
response = api.post_plugin_setting_archive(plugin_settings_id, zip_path)
|
|
38
|
-
paths.plugin_config.write(response.dig('data', 'settings_yaml'))
|
|
39
|
-
|
|
40
|
-
size = File.size(zip_path)
|
|
41
|
-
|
|
42
|
-
output <<~HEREDOC
|
|
43
|
-
Uploaded plugin (#{size} bytes)
|
|
44
|
-
Dashboard: #{config.app.edit_plugin_settings_uri(plugin_settings_id)}
|
|
45
|
-
HEREDOC
|
|
46
|
-
|
|
47
|
-
if is_new
|
|
48
|
-
output <<~HEREDOC
|
|
49
|
-
|
|
50
|
-
IMPORTANT! Don't forget to add it to your device playlist!
|
|
51
|
-
|
|
52
|
-
#{config.app.playlists_uri}
|
|
53
|
-
HEREDOC
|
|
54
|
-
end
|
|
55
|
-
rescue
|
|
56
|
-
if is_new && plugin_settings_id
|
|
57
|
-
output 'Error during creation, cleaning up...'
|
|
58
|
-
api.delete_plugin_setting(plugin_settings_id)
|
|
59
|
-
end
|
|
60
|
-
|
|
61
|
-
raise
|
|
62
|
-
ensure
|
|
63
|
-
File.delete(zip_path) if File.exist?(zip_path)
|
|
64
|
-
end
|
|
65
|
-
end
|
|
66
|
-
end
|
|
67
|
-
end
|
|
@@ -1,25 +0,0 @@
|
|
|
1
|
-
require 'zip'
|
|
2
|
-
|
|
3
|
-
require_relative 'base'
|
|
4
|
-
require_relative '../api_client'
|
|
5
|
-
|
|
6
|
-
module TRMNLP
|
|
7
|
-
module Commands
|
|
8
|
-
class Serve < Base
|
|
9
|
-
def call
|
|
10
|
-
context.validate!
|
|
11
|
-
|
|
12
|
-
# Must come AFTER parsing options
|
|
13
|
-
require_relative '../app'
|
|
14
|
-
|
|
15
|
-
# Now we can configure things
|
|
16
|
-
App.set(:context, context)
|
|
17
|
-
App.set(:bind, options.bind)
|
|
18
|
-
App.set(:port, options.port)
|
|
19
|
-
|
|
20
|
-
# Finally, start the app!
|
|
21
|
-
App.run!
|
|
22
|
-
end
|
|
23
|
-
end
|
|
24
|
-
end
|
|
25
|
-
end
|
data/lib/trmnlp/commands.rb
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
Dir[File.join(__dir__, 'commands', '*.rb')].each { |file| require file }
|
data/lib/trmnlp/config/app.rb
DELETED
|
@@ -1,47 +0,0 @@
|
|
|
1
|
-
require 'yaml'
|
|
2
|
-
|
|
3
|
-
module TRMNLP
|
|
4
|
-
class Config
|
|
5
|
-
# Stores trmnlp-wide configuration (irrespective of the current plugin)
|
|
6
|
-
class App
|
|
7
|
-
def initialize(paths)
|
|
8
|
-
@paths = paths
|
|
9
|
-
@config = read_config
|
|
10
|
-
end
|
|
11
|
-
|
|
12
|
-
def save
|
|
13
|
-
paths.app_config_dir.mkpath
|
|
14
|
-
paths.app_config.write(YAML.dump(@config))
|
|
15
|
-
end
|
|
16
|
-
|
|
17
|
-
def logged_in? = api_key && !api_key.empty?
|
|
18
|
-
def logged_out? = !logged_in?
|
|
19
|
-
|
|
20
|
-
def api_key
|
|
21
|
-
env_api_key = ENV['TRMNL_API_KEY']
|
|
22
|
-
return env_api_key if env_api_key && !env_api_key.empty?
|
|
23
|
-
@config['api_key']
|
|
24
|
-
end
|
|
25
|
-
|
|
26
|
-
def api_key=(key)
|
|
27
|
-
@config['api_key'] = key
|
|
28
|
-
end
|
|
29
|
-
|
|
30
|
-
def base_uri = URI.parse(@config['base_url'] || 'https://trmnl.com')
|
|
31
|
-
|
|
32
|
-
def api_uri = URI.join(base_uri, '/api')
|
|
33
|
-
|
|
34
|
-
def account_uri = URI.join(base_uri, '/account')
|
|
35
|
-
|
|
36
|
-
def edit_plugin_settings_uri(id) = URI.join(base_uri, "/plugin_settings/#{id.to_s}/edit")
|
|
37
|
-
|
|
38
|
-
def playlists_uri = URI.join(base_uri, '/playlists')
|
|
39
|
-
|
|
40
|
-
private
|
|
41
|
-
|
|
42
|
-
attr_reader :paths
|
|
43
|
-
|
|
44
|
-
def read_config = paths.app_config.exist? ? YAML.safe_load(paths.app_config.read) : {}
|
|
45
|
-
end
|
|
46
|
-
end
|
|
47
|
-
end
|