containers 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: 10eb220c07fba010dcc7f06bfbece1feef00f33f7521ea6c64422e0158d5f4b2
4
+ data.tar.gz: fc61199216e1aa3fe368d5a26b98b775a31cf3ac0a6723fae29c25d0fe5f9912
5
+ SHA512:
6
+ metadata.gz: 9d597a36e082a8d692de221f41e60d07a38bb509cf08e56d47123178ee680bd46af86f8981b57aef772772a4da587976c5894da36f943127ec5b259d50cd6d07
7
+ data.tar.gz: 50dc68c00349412c3f74a799a0c47b054dea7cdd8d078a9c87987a3d79b2f84d42fbd6540414ccb00b5757b6bfcea09ccce1dd09b688b8769e473fbca4d1f040
data/Gemfile ADDED
@@ -0,0 +1,9 @@
1
+ # frozen_string_literal: true
2
+
3
+ source "https://rubygems.org"
4
+
5
+ # Specify your gem's dependencies in containers.gemspec
6
+ gemspec
7
+
8
+ gem "rake", "~> 13.0"
9
+ gem "minitest", "~> 5.0"
data/Gemfile.lock ADDED
@@ -0,0 +1,106 @@
1
+ PATH
2
+ remote: .
3
+ specs:
4
+ containers (0.1.0)
5
+ rainbow (~> 3.1.1)
6
+ thor (~> 1.2.1)
7
+
8
+ GEM
9
+ remote: https://rubygems.org/
10
+ specs:
11
+ activesupport (7.0.3.1)
12
+ concurrent-ruby (~> 1.0, >= 1.0.2)
13
+ i18n (>= 1.6, < 2)
14
+ minitest (>= 5.1)
15
+ tzinfo (~> 2.0)
16
+ addressable (2.8.0)
17
+ public_suffix (>= 2.0.2, < 5.0)
18
+ async (2.0.3)
19
+ console (~> 1.10)
20
+ io-event (~> 1.0.0)
21
+ timers (~> 4.1)
22
+ async-http (0.56.6)
23
+ async (>= 1.25)
24
+ async-io (>= 1.28)
25
+ async-pool (>= 0.2)
26
+ protocol-http (~> 0.22.0)
27
+ protocol-http1 (~> 0.14.0)
28
+ protocol-http2 (~> 0.14.0)
29
+ traces (~> 0.4.0)
30
+ async-http-faraday (0.11.0)
31
+ async-http (~> 0.42)
32
+ faraday
33
+ async-io (1.33.0)
34
+ async
35
+ async-pool (0.3.10)
36
+ async (>= 1.25)
37
+ byebug (11.1.3)
38
+ coderay (1.1.3)
39
+ concurrent-ruby (1.1.10)
40
+ console (1.15.3)
41
+ fiber-local
42
+ faraday (2.3.0)
43
+ faraday-net_http (~> 2.0)
44
+ ruby2_keywords (>= 0.0.4)
45
+ faraday-http-cache (2.4.0)
46
+ faraday (>= 0.8)
47
+ faraday-net_http (2.0.3)
48
+ fiber-local (1.0.0)
49
+ github_changelog_generator (1.16.4)
50
+ activesupport
51
+ async (>= 1.25.0)
52
+ async-http-faraday
53
+ faraday-http-cache
54
+ multi_json
55
+ octokit (~> 4.6)
56
+ rainbow (>= 2.2.1)
57
+ rake (>= 10.0)
58
+ i18n (1.12.0)
59
+ concurrent-ruby (~> 1.0)
60
+ io-event (1.0.9)
61
+ method_source (1.0.0)
62
+ minitest (5.16.2)
63
+ multi_json (1.15.0)
64
+ octokit (4.25.1)
65
+ faraday (>= 1, < 3)
66
+ sawyer (~> 0.9)
67
+ protocol-hpack (1.4.2)
68
+ protocol-http (0.22.6)
69
+ protocol-http1 (0.14.4)
70
+ protocol-http (~> 0.22)
71
+ protocol-http2 (0.14.2)
72
+ protocol-hpack (~> 1.4)
73
+ protocol-http (~> 0.18)
74
+ pry (0.13.1)
75
+ coderay (~> 1.1)
76
+ method_source (~> 1.0)
77
+ public_suffix (4.0.7)
78
+ rainbow (3.1.1)
79
+ rake (13.0.6)
80
+ ruby2_keywords (0.0.5)
81
+ ruby_jard (0.3.1)
82
+ byebug (>= 9.1, < 12.0)
83
+ pry (~> 0.13.0)
84
+ tty-screen (~> 0.8.1)
85
+ sawyer (0.9.2)
86
+ addressable (>= 2.3.5)
87
+ faraday (>= 0.17.3, < 3)
88
+ thor (1.2.1)
89
+ timers (4.3.3)
90
+ traces (0.4.1)
91
+ tty-screen (0.8.1)
92
+ tzinfo (2.0.5)
93
+ concurrent-ruby (~> 1.0)
94
+
95
+ PLATFORMS
96
+ arm64-darwin-21
97
+
98
+ DEPENDENCIES
99
+ containers!
100
+ github_changelog_generator (~> 1.16.4)
101
+ minitest (~> 5.0)
102
+ rake (~> 13.0)
103
+ ruby_jard (~> 0.3.1)
104
+
105
+ BUNDLED WITH
106
+ 2.3.17
data/LICENSE.txt ADDED
@@ -0,0 +1,21 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2022 Hopsoft
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in
13
+ all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21
+ THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,24 @@
1
+ # Containers
2
+
3
+ ## TODOs
4
+
5
+ ### Questions to prompt on generate
6
+
7
+ - [ ] container logging?
8
+ - [ ] admin tooling?
9
+
10
+ #### Punt on these for now
11
+
12
+ ```
13
+ containers generate compose
14
+ containers add anycable
15
+ containers remove anycable
16
+ ```
17
+
18
+ - [ ] sinatra?
19
+ - [ ] rails?
20
+ - [ ] anycable?
21
+ - [ ] actioncable?
22
+ - [ ] caching? (redis)
23
+ - [ ] background jobs?
24
+ - [ ] backend? (sidekiq, ...)
data/Rakefile ADDED
@@ -0,0 +1,12 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "bundler/gem_tasks"
4
+ require "rake/testtask"
5
+
6
+ Rake::TestTask.new(:test) do |t|
7
+ t.libs << "test"
8
+ t.libs << "lib"
9
+ t.test_files = FileList["test/**/test_*.rb"]
10
+ end
11
+
12
+ task default: :test
@@ -0,0 +1,42 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative "lib/containers/version"
4
+
5
+ Gem::Specification.new do |gem|
6
+ gem.name = "containers"
7
+ gem.version = Containers::VERSION
8
+ gem.authors = ["Hopsoft"]
9
+ gem.email = ["natehop@gmail.com"]
10
+
11
+ gem.summary = "Manage local development environments with Docker"
12
+ gem.description = "Manage local development environments with Docker"
13
+ gem.homepage = "https://github.com/hopsoft/containers"
14
+ gem.license = "MIT"
15
+ gem.required_ruby_version = ">= 2.6.0"
16
+
17
+ # gem.metadata["allowed_push_host"] = "TODO: Set to your gem server 'https://example.com'"
18
+
19
+ gem.metadata["homepage_uri"] = gem.homepage
20
+ gem.metadata["source_code_uri"] = gem.homepage
21
+ gem.metadata["changelog_uri"] = "#{gem.homepage}/CHANGELOG.md"
22
+
23
+ # Specify which files should be added to the gem when it is released.
24
+ # The `git ls-files -z` loads the files in the RubyGem that have been added into git.
25
+ gem.files = Dir.chdir(File.expand_path(__dir__)) do
26
+ `git ls-files -z`.split("\x0").reject do |f|
27
+ (f == __FILE__) || f.match(%r{\A(?:(?:bin|test|spec|features)/|\.(?:git|travis|circleci)|appveyor)})
28
+ end
29
+ end
30
+ gem.bindir = "exe"
31
+ gem.executables = gem.files.grep(%r{\Aexe/}) { |f| File.basename(f) }
32
+ gem.require_paths = ["lib"]
33
+
34
+ gem.add_dependency "rainbow", "~> 3.1.1"
35
+ gem.add_dependency "thor", "~> 1.2.1"
36
+
37
+ gem.add_development_dependency "github_changelog_generator", "~> 1.16.4"
38
+ gem.add_development_dependency "ruby_jard", "~> 0.3.1"
39
+
40
+ # For more information and examples about making a new gem, check out our
41
+ # guide at: https://bundler.io/guides/creating_gem.html
42
+ end
data/exe/containers ADDED
@@ -0,0 +1,5 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "containers"
4
+
5
+ Containers::CLI.start(ARGV)
@@ -0,0 +1,141 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "thor"
4
+ require "rainbow"
5
+ require_relative "./generator"
6
+
7
+ module Containers
8
+ class CLI < Thor
9
+ COMMAND_PREFIX = "▶"
10
+
11
+ alias_method :execute, :exec
12
+
13
+ desc "generate", "Commands used to generate files for the project"
14
+ subcommand "generate", Generator
15
+
16
+ desc "up", "Brings up the environment defined in docker-compose.yml"
17
+ def up(*args)
18
+ execute_command "docker compose up -d #{args.join " "}"
19
+ end
20
+
21
+ desc "down", "Tears down the environment defined in docker-compose.yml"
22
+ def down(*args)
23
+ execute_command "docker compose down #{args.join " "}"
24
+ end
25
+
26
+ desc "list", "Lists all containers for this project"
27
+ method_option :detailed, type: :boolean, aliases: "-d", desc: "List detailed container information"
28
+ method_option :service, type: :boolean, aliases: "-s", desc: "List container service names"
29
+ def list(*args)
30
+ return execute_command "docker ps -a | grep #{project_name}" if options[:detailed]
31
+
32
+ if options[:service]
33
+ command = "containers list -f"
34
+ puts_command "#{command} | #{Rainbow("(strip project name)").green.faint}"
35
+ list = `#{command}`.split("\n").reject { |item| item.strip == "" || item.include?(COMMAND_PREFIX) }
36
+ puts list.map { |item| item.gsub(/\A#{project_name}-|\s/, "") }.sort.join("\n")
37
+ return
38
+ end
39
+
40
+ command = "containers list -d"
41
+ puts_command "#{command} | #{Rainbow("(strip docker details)").green.faint}"
42
+ list = `#{command}`.split("\n").reject { |item| item.strip == "" || item.include?(COMMAND_PREFIX) }
43
+ puts list.map { |item| item.split(" ").last.strip }.sort.join("\n")
44
+ end
45
+
46
+ desc "inspect", "Inspects a container"
47
+ method_option :container, type: :string, aliases: "-c", required: true, desc: "The short name for the container"
48
+ def inspect(*args)
49
+ execute_command "docker inspect #{args.join " "} #{project_name}-#{options[:container]}"
50
+ end
51
+
52
+ desc "attach", "Attaches to a running container"
53
+ method_option :container, type: :string, aliases: "-c", required: true, desc: "The short name for the container"
54
+ def attach(*args)
55
+ execute_command "docker attach #{project_name}-#{options[:container]} #{args.join " "}"
56
+ end
57
+
58
+ desc "exec", "Executes a command in a container"
59
+ method_option :container, type: :string, aliases: "-c", default: "shell", desc: "The short name for the container"
60
+ def exec(*args)
61
+ options[:container] = "shell" if options[:container].to_s.strip == ""
62
+ execute_command "docker exec -it #{project_name}-#{options[:container]} #{args.join " "}"
63
+ end
64
+
65
+ desc "tail", "Tails container logs"
66
+ method_option :container, type: :array, aliases: "-c", required: true, desc: "The short name for the container (also supports a list of names)"
67
+ def tail(*args)
68
+ args << "--since 5m" unless args.include?("--since")
69
+ execute_command "docker compose logs #{args.join " "} -f #{options[:container].join " "}"
70
+ end
71
+
72
+ desc "start", "Starts container(s)"
73
+ method_option :container, type: :string, aliases: "-c", desc: "The short name for the container"
74
+ def start(*args)
75
+ return execute_command "docker start #{args.join " "} #{project_name}-#{options[:container]}" if options[:container]
76
+ container_names.each { |c| execute_command "docker start #{args.join " "} #{c}", replace_current_process: false }
77
+ end
78
+
79
+ desc "stop", "Stops container(s)"
80
+ method_option :container, type: :string, aliases: "-c", desc: "The short name for the container"
81
+ def stop(*args)
82
+ return execute_command "docker stop #{args.join " "} #{project_name}-#{options[:container]}" if options[:container]
83
+ container_names.each { |c| execute_command "docker stop #{args.join " "} #{c}", replace_current_process: false }
84
+ end
85
+
86
+ desc "restart", "Restarts container(s)"
87
+ method_option :container, type: :array, aliases: "-c", desc: "A list of container short names"
88
+ def restart(*args)
89
+ containers = options[:container] || container_names
90
+ containers.each { |c| execute_command "docker restart #{args.join " "} #{c}", replace_current_process: false }
91
+ end
92
+
93
+ desc "bash", "Starts a bash shell"
94
+ method_option :container, type: :string, aliases: "-c", default: "shell", desc: "The short name for the container"
95
+ def bash(*args)
96
+ execute_command "containers exec -c #{options[:container]} bash #{args.join " "}"
97
+ end
98
+
99
+ desc "bundle", "Runs the bundle command"
100
+ method_option :container, type: :string, aliases: "-c", default: "shell", desc: "The short name for the container"
101
+ def bundle(*args)
102
+ execute_command "containers exec -c #{options[:container]} bundle #{args.join " "}"
103
+ end
104
+
105
+ desc "yarn", "Runs the yarn command"
106
+ method_option :container, type: :string, aliases: "-c", default: "shell", desc: "The short name for the container"
107
+ def yarn(*args)
108
+ execute_command "containers exec -c #{options[:container]} yarn #{args.join " "}"
109
+ end
110
+
111
+ desc "rails", "Runs the Rails command"
112
+ method_option :container, type: :string, aliases: "-c", default: "shell", desc: "The short name for the container"
113
+ def rails(*args)
114
+ execute_command "containers bundle -c #{options[:container]} exec rails #{args.join " "}"
115
+ end
116
+
117
+ private
118
+
119
+ def container_names
120
+ `containers list -f`.split("\n")
121
+ end
122
+
123
+ def project_name
124
+ squish(File.basename(Dir.pwd)).gsub(/\s|_/, "-")
125
+ end
126
+
127
+ def squish(string)
128
+ string.gsub(/\s+/, " ").strip
129
+ end
130
+
131
+ def execute_command(command, replace_current_process: true)
132
+ command = squish(command)
133
+ puts_command command
134
+ replace_current_process ? execute(command) : puts(`#{command}`)
135
+ end
136
+
137
+ def puts_command(command)
138
+ puts "#{Rainbow(COMMAND_PREFIX).green.faint} #{Rainbow(command).green.bright}"
139
+ end
140
+ end
141
+ end
@@ -0,0 +1,40 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "erb"
4
+
5
+ class Generator < Thor
6
+ desc "dockerfile", "Creates a Dockerfile for the project"
7
+ def dockerfile
8
+ path = File.expand_path("Dockerfile")
9
+
10
+ continue = if File.exist?(path)
11
+ ask("#{Rainbow("Dockerfile already exists").red} Overwrite?", default: "Y").to_s.upcase == "Y"
12
+ else
13
+ true
14
+ end
15
+
16
+ return unless continue
17
+
18
+ ruby_version = ask("What Ruby version does this project use?", default: "3.1.2").to_s
19
+ File.write path, render("Dockerfile", ruby_version: ruby_version)
20
+ end
21
+
22
+ desc "compose", "Creates a docker-compose.yml file for the project"
23
+ def compose
24
+ end
25
+
26
+ private
27
+
28
+ def root_path
29
+ File.expand_path(File.join(__dir__, "..", ".."))
30
+ end
31
+
32
+ def template(name)
33
+ ERB.new(File.read(File.join(root_path, "lib/containers/templates/#{name}.erb")))
34
+ end
35
+
36
+ def render(template_name, vars = {})
37
+ view = Struct.new(*vars.keys).new(*vars.values).instance_eval { binding }
38
+ template(template_name).result view
39
+ end
40
+ end
@@ -0,0 +1,26 @@
1
+ FROM ruby:<%= ruby_version %>-alpine
2
+
3
+ RUN apk add --no-cache --update \
4
+ ack \
5
+ bash \
6
+ build-base \
7
+ cloc \
8
+ curl \
9
+ git \
10
+ htop \
11
+ less \
12
+ libc6-compat \
13
+ libsass \
14
+ linux-headers \
15
+ nodejs \
16
+ npm \
17
+ postgresql-client \
18
+ postgresql-dev \
19
+ redis \
20
+ tzdata \
21
+ vim \
22
+ yarn
23
+
24
+ RUN gem install bundler
25
+
26
+ CMD tail -f /dev/null
@@ -0,0 +1,217 @@
1
+ version: "3.9"
2
+
3
+ # Ports exposed on the host machine
4
+ #
5
+ # Note: These can be overridden with environment variables
6
+ #
7
+ # - PORT_RAILS=3000 ...... The primary Rails web application
8
+ # - PORT_ANYCABLE=3001 ... The AnyCable server
9
+ # - PORT_LOGS=3002 ....... Web interface for viewing all Docker container logs
10
+
11
+ x-default-env: &default_env
12
+ BUNDLE_PATH: /bundle
13
+ EDITOR: /usr/bin/vim
14
+
15
+ x-default-app: &default_app
16
+ build: .
17
+ image: <%= organization_name %>/<%= project_name %>
18
+ working_dir: /<%= project_name %>
19
+ tty: true
20
+ stdin_open: true
21
+ env_file: .env
22
+ environment:
23
+ <<: *default_env
24
+ networks:
25
+ - main
26
+ volumes:
27
+ - ./:/<%= project_name %>:cached
28
+ - bundle:/bundle:delegated
29
+ - node_modules:/<%= project_name %>/node_modules:delegated
30
+
31
+ networks:
32
+ main:
33
+
34
+ # TODO: dump pg database then rename db -> postgres
35
+ volumes:
36
+ bundle:
37
+ db:
38
+ node_modules:
39
+ redis_cable:
40
+ redis_cache:
41
+ redis_queue:
42
+
43
+ services:
44
+ # ----------------------------------------------------------------------------
45
+ # Postgres - Primary database server
46
+ # ----------------------------------------------------------------------------
47
+ postgres:
48
+ image: postgres:13.4-alpine3.14
49
+ container_name: <%= project_name %>-postgres
50
+ restart: unless-stopped
51
+ environment:
52
+ POSTGRES_PASSWORD: password
53
+ networks:
54
+ - main
55
+ expose:
56
+ - 5432
57
+ volumes:
58
+ - db:/var/lib/postgresql/data:delegated
59
+
60
+ # ----------------------------------------------------------------------------
61
+ # Redis - ActionCable datastore
62
+ # ----------------------------------------------------------------------------
63
+ redis_cable:
64
+ image: redis:6.2.6-alpine3.14
65
+ container_name: <%= project_name %>-redis-cable
66
+ restart: unless-stopped
67
+ networks:
68
+ - main
69
+ expose:
70
+ - 6379
71
+ volumes:
72
+ - redis_cable:/data:delegated
73
+ - ./config/redis-queue.conf:/usr/local/etc/redis/redis.conf:cached
74
+
75
+ # ----------------------------------------------------------------------------
76
+ # Redis - Cache datastore
77
+ # ----------------------------------------------------------------------------
78
+ redis_cache:
79
+ image: redis:6.2.6-alpine3.14
80
+ container_name: <%= project_name %>-redis-cache
81
+ restart: unless-stopped
82
+ networks:
83
+ - main
84
+ expose:
85
+ - 6379
86
+ volumes:
87
+ - redis_cache:/data:delegated
88
+ - ./config/redis-cache.conf:/usr/local/etc/redis/redis.conf:cached
89
+
90
+ # ----------------------------------------------------------------------------
91
+ # Redis - Queue datastore
92
+ # ----------------------------------------------------------------------------
93
+ redis_queue:
94
+ image: redis:6.2.6-alpine3.14
95
+ container_name: <%= project_name %>-redis-queue
96
+ restart: unless-stopped
97
+ networks:
98
+ - main
99
+ expose:
100
+ - 6379
101
+ volumes:
102
+ - redis_queue:/data:delegated
103
+ - ./config/redis-queue.conf:/usr/local/etc/redis/redis.conf:cached
104
+
105
+ # ----------------------------------------------------------------------------
106
+ # Shell - Intended for tinkering and running misc commands
107
+ # ----------------------------------------------------------------------------
108
+ shell:
109
+ <<: *default_app
110
+ container_name: <%= project_name %>-shell
111
+ command: /bin/bash -c "tail -f /dev/null"
112
+
113
+ # ----------------------------------------------------------------------------
114
+ # JavaScript - Builds JavaScript assets
115
+ # ----------------------------------------------------------------------------
116
+ js:
117
+ <<: *default_app
118
+ container_name: <%= project_name %>-js
119
+ command: /bin/bash -c "yarn && yarn build --watch"
120
+
121
+ # ----------------------------------------------------------------------------
122
+ # CSS - Builds CSS stylesheet assets
123
+ # ----------------------------------------------------------------------------
124
+ css:
125
+ <<: *default_app
126
+ container_name: <%= project_name %>-css
127
+ command: /bin/bash -c "yarn build:css --watch"
128
+ depends_on:
129
+ - js
130
+
131
+ # ----------------------------------------------------------------------------
132
+ # Rails - The primary Rails web application
133
+ # ----------------------------------------------------------------------------
134
+ web:
135
+ <<: *default_app
136
+ container_name: <%= project_name %>-web
137
+ command: >
138
+ /bin/bash -c "bundle &&
139
+ rm -f tmp/pids/server.pid &&
140
+ touch tmp/caching-dev.txt &&
141
+ bin/rails log:clear &&
142
+ bin/rails db:create db:migrate &&
143
+ bin/rails s --binding=0.0.0.0 --port=3000"
144
+ environment:
145
+ <<: *default_env
146
+ ports:
147
+ - ${PORT_RAILS_WEB:-3000}:3000
148
+ depends_on:
149
+ - postgres
150
+ - redis_cable
151
+ - redis_cache
152
+ - redis_queue
153
+ - js
154
+ - css
155
+
156
+ # ----------------------------------------------------------------------------
157
+ # Rails - Sidekiq worker for: config/sidekiq.yml
158
+ # ----------------------------------------------------------------------------
159
+ worker:
160
+ <<: *default_app
161
+ container_name: <%= project_name %>-worker
162
+ command: /bin/bash -c "bin/rails log:clear &&
163
+ bundle exec sidekiq -C config/sidekiq.yml"
164
+ depends_on:
165
+ - web
166
+
167
+ # ----------------------------------------------------------------------------
168
+ # Anycable - Web socket server
169
+ # ----------------------------------------------------------------------------
170
+ anycable_ws:
171
+ image: anycable/anycable-go:1.2
172
+ container_name: <%= project_name %>-anycable-ws
173
+ restart: unless-stopped
174
+ environment:
175
+ ANYCABLE_HOST: "0.0.0.0"
176
+ ANYCABLE_REDIS_URL: redis://redis_cable:6379/0
177
+ ANYCABLE_RPC_HOST: anycable_rpc:50051
178
+ ANYCABLE_DEBUG: 1
179
+ networks:
180
+ - main
181
+ ports:
182
+ - ${PORT_ANYCABLE:-3001}:8080
183
+ depends_on:
184
+ - redis_cable
185
+
186
+ # ----------------------------------------------------------------------------
187
+ # Anycable - Web socket gRPC server (bridge to ws server)
188
+ # ----------------------------------------------------------------------------
189
+ anycable_rpc:
190
+ <<: *default_app
191
+ container_name: <%= project_name %>-anycable-rpc
192
+ restart: unless-stopped
193
+ environment:
194
+ <<: *default_env
195
+ ANYCABLE_REDIS_URL: redis://redis_cable:6379/0
196
+ ANYCABLE_RPC_HOST: 0.0.0.0:50051
197
+ ANYCABLE_DEBUG: 1
198
+ networks:
199
+ - main
200
+ command: /bin/bash -c "bundle exec anycable"
201
+ depends_on:
202
+ - anycable_ws
203
+ - web
204
+
205
+ # ----------------------------------------------------------------------------
206
+ # Dozzle - Realtime log viewer for docker containers
207
+ # https://github.com/amir20/dozzle
208
+ # ----------------------------------------------------------------------------
209
+ logs:
210
+ image: amir20/dozzle
211
+ container_name: <%= project_name %>-logs
212
+ volumes:
213
+ - /var/run/docker.sock:/var/run/docker.sock
214
+ ports:
215
+ - ${PORT_LOGS:-3004}:8080
216
+ restart: unless-stopped
217
+ command: "--filter name=<%= project_name %>*"