exogress 0.0.1.pre.alpha.1

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: 42d872bfac64e0884243c5d88749bb49f8b41e252fcafbf2728b477ccb7e9008
4
+ data.tar.gz: acc49bfacac41bfa1846708b2a1beeb59cf21ea2ef460c9be0c9a29d580bed60
5
+ SHA512:
6
+ metadata.gz: 2c475a896a86f6d55086deb8bb7ef09510b83373a87a7400b500265c5e95738d17b2e6b43d9bcd44bf82d037a9bceeb3011e2ac00735b9dcb281703fadc0451e
7
+ data.tar.gz: d8d0eacd302e4ac60c828a748c63cafa037c92f6695e4eb45a20a61dc1dd7f8fa42923c688aed16a69be53a1d0629e807f8e078b8500925624928e1f73ed711f
@@ -0,0 +1,29 @@
1
+ name: Ruby
2
+
3
+ on: [push,pull_request]
4
+
5
+ jobs:
6
+ build:
7
+ runs-on: ubuntu-latest
8
+ steps:
9
+ - uses: actions/checkout@v2
10
+ - name: Set up Ruby
11
+ uses: ruby/setup-ruby@v1
12
+ with:
13
+ ruby-version: 3.0.1
14
+
15
+ - name: Build and publish
16
+ run: |
17
+ gem install bundler -v 2.2.15
18
+ bundle install
19
+ bundle exec rake build
20
+
21
+ - name: Publish to RubyGems
22
+ run: |
23
+ mkdir -p $HOME/.gem
24
+ touch $HOME/.gem/credentials
25
+ chmod 0600 $HOME/.gem/credentials
26
+ printf -- "---\n:rubygems_api_key: ${GEM_HOST_API_KEY}\n" > $HOME/.gem/credentials
27
+ gem push pkg/*.gem
28
+ env:
29
+ GEM_HOST_API_KEY: "${{secrets.RUBYGEMS_API_KEY}}"
data/.gitignore ADDED
@@ -0,0 +1,14 @@
1
+ /target
2
+ Cargo.lock
3
+
4
+ /.bundle/
5
+ /.yardoc
6
+ /_yardoc/
7
+ /coverage/
8
+ /doc/
9
+ /pkg/
10
+ /spec/reports/
11
+ /tmp/
12
+
13
+ # rspec failure tracking
14
+ .rspec_status
data/.idea/.gitignore ADDED
@@ -0,0 +1,8 @@
1
+ # Default ignored files
2
+ /shelf/
3
+ /workspace.xml
4
+ # Datasource local storage ignored files
5
+ /dataSources/
6
+ /dataSources.local.xml
7
+ # Editor-based HTTP Client requests
8
+ /httpRequests/
@@ -0,0 +1,11 @@
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <module type="CPP_MODULE" version="4">
3
+ <component name="NewModuleRootManager">
4
+ <content url="file://$MODULE_DIR$">
5
+ <sourceFolder url="file://$MODULE_DIR$/src" isTestSource="false" />
6
+ <excludeFolder url="file://$MODULE_DIR$/target" />
7
+ </content>
8
+ <orderEntry type="inheritedJdk" />
9
+ <orderEntry type="sourceFolder" forTests="false" />
10
+ </component>
11
+ </module>
data/.idea/modules.xml ADDED
@@ -0,0 +1,8 @@
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <project version="4">
3
+ <component name="ProjectModuleManager">
4
+ <modules>
5
+ <module fileurl="file://$PROJECT_DIR$/.idea/exogress-ruby.iml" filepath="$PROJECT_DIR$/.idea/exogress-ruby.iml" />
6
+ </modules>
7
+ </component>
8
+ </project>
data/.idea/vcs.xml ADDED
@@ -0,0 +1,7 @@
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <project version="4">
3
+ <component name="VcsDirectoryMappings">
4
+ <mapping directory="$PROJECT_DIR$" vcs="Git" />
5
+ <mapping directory="$PROJECT_DIR$/exogress" vcs="Git" />
6
+ </component>
7
+ </project>
data/.rspec ADDED
@@ -0,0 +1,3 @@
1
+ --format documentation
2
+ --color
3
+ --require spec_helper
data/Cargo.toml ADDED
@@ -0,0 +1,21 @@
1
+ [package]
2
+ name = "exogress-ruby"
3
+ version = "0.0.1-alpha.1"
4
+ edition = "2018"
5
+
6
+ [dependencies]
7
+ rutie = "0.8.2"
8
+ exogress-common = { git = "https://github.com/exogress/exogress.git", branch = "master", version = "0.2.0", features = ["client-core", "tunnel", "config-core", "entities", "common-utils"], default-features = false }
9
+ futures = "0.3.5"
10
+ trust-dns-resolver = "0.20.0"
11
+ hashbrown = "0.11.2"
12
+ tokio = { version = "1.0", features = ["macros", "rt-multi-thread", "rt", "parking_lot"] }
13
+ anyhow = "1.0.41"
14
+ #log = "0.4.14"
15
+ parking_lot = "0.11.1"
16
+ lazy_static = "1.4.0"
17
+
18
+ [lib]
19
+ name = "rutie_exogress"
20
+ crate-type = ["cdylib"]
21
+
data/Exofile.yml ADDED
@@ -0,0 +1,14 @@
1
+ ---
2
+ version: 1.1.0
3
+ revision: 1
4
+ name: default
5
+ mount-points:
6
+ default:
7
+ handlers:
8
+ proxy:
9
+ kind: proxy
10
+ priority: 50
11
+ upstream: backend
12
+ upstreams:
13
+ backend:
14
+ port: 4001
data/Gemfile ADDED
@@ -0,0 +1,11 @@
1
+ # frozen_string_literal: true
2
+
3
+ source "https://rubygems.org"
4
+
5
+ # Specify your gem's dependencies in exogress.gemspec
6
+ gemspec
7
+
8
+ gem "rake", "~> 13.0"
9
+
10
+ gem "rspec", "~> 3.0"
11
+ gem 'rutie', '~> 0.0.4'
data/Gemfile.lock ADDED
@@ -0,0 +1,39 @@
1
+ PATH
2
+ remote: .
3
+ specs:
4
+ exogress (0.0.1.pre.alpha.1)
5
+ rutie (~> 0.0.4)
6
+
7
+ GEM
8
+ remote: https://rubygems.org/
9
+ specs:
10
+ diff-lcs (1.4.4)
11
+ rake (13.0.3)
12
+ rspec (3.10.0)
13
+ rspec-core (~> 3.10.0)
14
+ rspec-expectations (~> 3.10.0)
15
+ rspec-mocks (~> 3.10.0)
16
+ rspec-core (3.10.1)
17
+ rspec-support (~> 3.10.0)
18
+ rspec-expectations (3.10.1)
19
+ diff-lcs (>= 1.2.0, < 2.0)
20
+ rspec-support (~> 3.10.0)
21
+ rspec-mocks (3.10.2)
22
+ diff-lcs (>= 1.2.0, < 2.0)
23
+ rspec-support (~> 3.10.0)
24
+ rspec-support (3.10.2)
25
+ rutie (0.0.4)
26
+
27
+ PLATFORMS
28
+ x86_64-darwin-20
29
+ x86_64-linux
30
+
31
+ DEPENDENCIES
32
+ bundler
33
+ exogress!
34
+ rake (~> 13.0)
35
+ rspec (~> 3.0)
36
+ rutie (~> 0.0.4)
37
+
38
+ BUNDLED WITH
39
+ 2.2.15
data/LICENSE.txt ADDED
@@ -0,0 +1,21 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2021 Gleb Pomykalov
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,39 @@
1
+ # Exogress
2
+
3
+ Welcome to your new gem! In this directory, you'll find the files you need to be able to package up your Ruby library into a gem. Put your Ruby code in the file `lib/exogress`. To experiment with that code, run `bin/console` for an interactive prompt.
4
+
5
+ TODO: Delete this and the text above, and describe your gem
6
+
7
+ ## Installation
8
+
9
+ Add this line to your application's Gemfile:
10
+
11
+ ```ruby
12
+ gem 'exogress'
13
+ ```
14
+
15
+ And then execute:
16
+
17
+ $ bundle install
18
+
19
+ Or install it yourself as:
20
+
21
+ $ gem install exogress
22
+
23
+ ## Usage
24
+
25
+ TODO: Write usage instructions here
26
+
27
+ ## Development
28
+
29
+ After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake spec` to run the tests. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
30
+
31
+ To install this gem onto your local machine, run `bundle exec rake install`. To release a new version, update the version number in `version.rb`, and then run `bundle exec rake release`, which will create a git tag for the version, push git commits and the created tag, and push the `.gem` file to [rubygems.org](https://rubygems.org).
32
+
33
+ ## Contributing
34
+
35
+ Bug reports and pull requests are welcome on GitHub at https://github.com/[USERNAME]/exogress.
36
+
37
+ ## License
38
+
39
+ The gem is available as open source under the terms of the [MIT License](https://opensource.org/licenses/MIT).
data/Rakefile ADDED
@@ -0,0 +1,36 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "bundler/gem_tasks"
4
+ require "rbconfig"
5
+
6
+ task default: :build_lib
7
+
8
+ # Mac OS with rbenv users keep leaving behind build artifacts from
9
+ # when they tried to build against a statically linked Ruby and then
10
+ # try against a dynamically linked one causing errors in the build result.
11
+ desc 'Preventative work'
12
+ task :tidy_up do
13
+ sh 'cargo clean'
14
+ end
15
+
16
+ desc 'Build Rust extension'
17
+ task :build_lib do
18
+ case RbConfig::CONFIG['host_os']
19
+ when /darwin|mac os/
20
+ sh 'cargo rustc --release -- -C link-args=-Wl,-undefined,dynamic_lookup'
21
+ else
22
+ sh 'cargo build --release'
23
+ end
24
+ end
25
+
26
+ desc 'bundle install'
27
+ task :bundle_install do
28
+ sh 'bundle install'
29
+ end
30
+
31
+ begin
32
+ require "rspec/core/rake_task"
33
+ RSpec::Core::RakeTask.new(spec: [:bundle_install, :build_lib]) do |t|
34
+ end
35
+ rescue LoadError
36
+ end
data/bin/console ADDED
@@ -0,0 +1,15 @@
1
+ #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
3
+
4
+ require "bundler/setup"
5
+ require "exogress"
6
+
7
+ # You can add fixtures and/or initialization code here to make experimenting
8
+ # with your gem easier. You can also use a different console, if you like.
9
+
10
+ # (If you use this, don't forget to add pry to your Gemfile!)
11
+ # require "pry"
12
+ # Pry.start
13
+
14
+ require "irb"
15
+ IRB.start(__FILE__)
data/bin/setup ADDED
@@ -0,0 +1,8 @@
1
+ #!/usr/bin/env bash
2
+ set -euo pipefail
3
+ IFS=$'\n\t'
4
+ set -vx
5
+
6
+ bundle install
7
+
8
+ # Do any other automated setup that you need to do here
@@ -0,0 +1,30 @@
1
+ require_relative "../lib/exogress"
2
+ require 'logger'
3
+
4
+ logger = Logger.new(STDOUT)
5
+ logger.level = Logger::WARN
6
+
7
+ Instance.set_logger(logger)
8
+ logger.info("Starting exogress.!")
9
+ instance = Instance.new({
10
+ access_key_id: "01F68JEA8XW0MM1XGGR47F7KSD",
11
+ secret_access_key: "a83Xj28xao6UkHRasZUhVVrrhc26w8RMJsyV7kkgn7jU",
12
+ account: "glebpom",
13
+ project: "location-tester",
14
+ labels: {
15
+ "label1": "val1",
16
+ }
17
+ })
18
+
19
+ Thread.new do
20
+ print("Spawn instance!")
21
+ instance.spawn()
22
+ print("instance stopped")
23
+ end
24
+
25
+ sleep(5)
26
+ print("reload")
27
+ instance.reload
28
+ sleep(5)
29
+ print("stop")
30
+ instance.stop
data/exogress.gemspec ADDED
@@ -0,0 +1,37 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative "lib/exogress/version"
4
+
5
+ Gem::Specification.new do |spec|
6
+ spec.name = "exogress"
7
+ spec.version = Exogress::VERSION
8
+ spec.authors = ["Exogress Team"]
9
+ spec.email = ["team@exogress.com"]
10
+
11
+ spec.summary = "Exogress client for Ruby"
12
+ spec.description = "Exogress is an edge network built for your cloud"
13
+ spec.homepage = "https://exogess.com"
14
+ spec.license = "Apache 2.0"
15
+ spec.required_ruby_version = Gem::Requirement.new(">= 2.4.0")
16
+
17
+ # spec.metadata["allowed_push_host"] = "TODO: Set to 'http://mygemserver.com'"
18
+
19
+ spec.metadata["homepage_uri"] = spec.homepage
20
+ spec.metadata["source_code_uri"] = "https://github.com/exogress/exogress-ruby"
21
+ # spec.metadata["changelog_uri"] = "TODO: Put your gem's CHANGELOG.md URL here."
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
+ spec.files = Dir.chdir(File.expand_path(__dir__)) do
26
+ `git ls-files -z`.split("\x0").reject { |f| f.match(%r{\A(?:test|spec|features)/}) }
27
+ end
28
+ spec.bindir = "exe"
29
+ spec.executables = spec.files.grep(%r{\Aexe/}) { |f| File.basename(f) }
30
+ spec.require_paths = ["lib"]
31
+ spec.extensions = %w(Rakefile)
32
+
33
+ spec.add_dependency 'rutie', '~> 0.0.4'
34
+ spec.add_development_dependency "bundler"
35
+ spec.add_development_dependency "rake", "~> 10.0"
36
+
37
+ end
data/lib/exogress.rb ADDED
@@ -0,0 +1,14 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative "exogress/version"
4
+ require 'rutie'
5
+
6
+ class ExogressError < StandardError
7
+ end
8
+
9
+ class EntityError < StandardError
10
+ end
11
+
12
+ module Exogress
13
+ Rutie.new(:rutie_exogress).init 'Init_rutie_exogress', __dir__
14
+ end
@@ -0,0 +1,5 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Exogress
4
+ VERSION = "0.0.1-alpha.1"
5
+ end
data/src/instance.rs ADDED
@@ -0,0 +1,308 @@
1
+ use lazy_static::lazy_static;
2
+
3
+ use rutie::{Class, Object, RString, VM, Hash, Symbol, AnyException, Boolean, NilClass};
4
+ use exogress_common::entities::{AccessKeyId, ProjectName, AccountName, LabelName, LabelValue};
5
+ use rutie::Exception;
6
+ use std::str::FromStr;
7
+ use hashbrown::HashMap;
8
+ use rutie::types::ValueType;
9
+ use futures::channel::mpsc::{self, UnboundedSender, UnboundedReceiver};
10
+ use futures::channel::oneshot;
11
+ use exogress_common::entities::SmolStr;
12
+ use exogress_common::client_core::Client;
13
+ use tokio::runtime::Runtime;
14
+ use trust_dns_resolver::TokioAsyncResolver;
15
+ use trust_dns_resolver::TokioHandle;
16
+ use rutie::Thread;
17
+ use std::sync::Arc;
18
+ use rutie::AnyObject;
19
+
20
+ const CRATE_VERSION: &'static str = env!("CARGO_PKG_VERSION");
21
+
22
+ pub struct RustInstance {
23
+ client: parking_lot::Mutex<Option<exogress_common::client_core::Client>>,
24
+ reload_config_tx: parking_lot::Mutex<UnboundedSender<()>>,
25
+ reload_config_rx: Arc<parking_lot::Mutex<Option<UnboundedReceiver<()>>>>,
26
+ stop_tx: parking_lot::Mutex<Option<oneshot::Sender<()>>>,
27
+ stop_rx: Arc<parking_lot::Mutex<Option<oneshot::Receiver<()>>>>,
28
+ }
29
+
30
+ wrappable_struct!(RustInstance, RustInstanceWrapper, INSTANCE_WRAPPER);
31
+
32
+ fn get_string_entity<T>(k: &str, args: &Hash) -> T
33
+ where
34
+ T: FromStr,
35
+ <T as FromStr>::Err: std::fmt::Display,
36
+ {
37
+ args
38
+ .at(&Symbol::new(k))
39
+ .try_convert_to::<RString>()
40
+ .map_err(|e| VM::raise_ex(e))
41
+ .unwrap()
42
+ .to_string()
43
+ .parse::<T>()
44
+ .map_err(|e| {
45
+ let exception = AnyException::new("EntityError", Some(e.to_string().as_str()));
46
+ VM::raise_ex(exception);
47
+ })
48
+ .unwrap()
49
+ }
50
+
51
+ fn get_string_entity_optional<T>(k: &str, args: &Hash) -> Option<T>
52
+ where
53
+ T: FromStr,
54
+ <T as FromStr>::Err: std::fmt::Display,
55
+ {
56
+ let val = args
57
+ .at(&Symbol::new(k));
58
+ if val.is_nil() {
59
+ return None;
60
+ } else {
61
+ Some(val
62
+ .try_convert_to::<RString>()
63
+ .map_err(|e| VM::raise_ex(e))
64
+ .unwrap()
65
+ .to_string()
66
+ .parse::<T>()
67
+ .map_err(|e| {
68
+ let exception = AnyException::new("EntityError", Some(e.to_string().as_str()));
69
+ VM::raise_ex(exception);
70
+ })
71
+ .unwrap())
72
+ }
73
+ }
74
+
75
+ fn get_bool_entity(k: &str, default: bool, args: &Hash) -> bool
76
+ {
77
+ let val = args
78
+ .at(&Symbol::new(k));
79
+ if val.is_nil() {
80
+ return default;
81
+ } else {
82
+ val
83
+ .try_convert_to::<Boolean>()
84
+ .map_err(|e| VM::raise_ex(e))
85
+ .unwrap()
86
+ .to_bool()
87
+ }
88
+ }
89
+
90
+ class!(Instance);
91
+
92
+ methods!(
93
+ Instance,
94
+ itself,
95
+
96
+ fn new(args: Hash) -> Class {
97
+ let args = args.map_err(|e| VM::raise_ex(e)).unwrap();
98
+ let account: AccountName = get_string_entity("account", &args);
99
+ let project: ProjectName = get_string_entity("project", &args);
100
+ let access_key_id: AccessKeyId = get_string_entity("access_key_id", &args);
101
+ let config_path: Option<String> = get_string_entity_optional("config_path", &args);
102
+ let watch_config = get_bool_entity("watch_config", true, &args);
103
+
104
+ let mut labels = hashbrown::HashMap::new();
105
+ let labels_ruby = args.at(&Symbol::new("labels"));
106
+ if labels_ruby.ty() == ValueType::Hash {
107
+ let labels_ruby = labels_ruby
108
+ .try_convert_to::<Hash>()
109
+ .map_err(|e| VM::raise_ex(e))
110
+ .unwrap();
111
+
112
+ labels_ruby.each(|k,v| {
113
+ let as_symbol = k
114
+ .try_convert_to::<Symbol>()
115
+ .map(|symbol| {
116
+ symbol
117
+ .to_string()
118
+ });
119
+
120
+ let k = as_symbol.unwrap_or_else(|_| {
121
+ k
122
+ .try_convert_to::<RString>()
123
+ .map_err(|e| VM::raise_ex(e))
124
+ .unwrap()
125
+ .to_string()
126
+ });
127
+
128
+ labels.insert(
129
+ k.parse::<LabelName>()
130
+ .map_err(|e| {
131
+ let exception = AnyException::new("EntityError", Some(e.to_string().as_str()));
132
+ VM::raise_ex(exception);
133
+ })
134
+ .unwrap(),
135
+ v
136
+ .try_convert_to::<RString>()
137
+ .map_err(|e| VM::raise_ex(e))
138
+ .unwrap()
139
+ .to_string()
140
+ .parse::<LabelValue>()
141
+ .map_err(|e| {
142
+ let exception = AnyException::new("EntityError", Some("bad label value"));
143
+ VM::raise_ex(exception);
144
+ })
145
+ .unwrap()
146
+ );
147
+ });
148
+ }
149
+ let secret_access_key = args
150
+ .at(&Symbol::new("secret_access_key"))
151
+ .try_convert_to::<RString>()
152
+ .map_err(|e| VM::raise_ex(e))
153
+ .unwrap()
154
+ .to_string();
155
+
156
+ let mut client_builder = Client::builder();
157
+
158
+ if let Some(config_path) = config_path {
159
+ client_builder.config_path(config_path);
160
+ }
161
+
162
+ let client = client_builder
163
+ .access_key_id(access_key_id.clone())
164
+ .secret_access_key(secret_access_key.clone())
165
+ .account(account.clone())
166
+ .project(project.clone())
167
+ .watch_config(watch_config)
168
+ .profile(None)
169
+ .labels(labels)
170
+ .additional_connection_params({
171
+ let mut map = HashMap::<SmolStr, SmolStr>::new();
172
+ map.insert("client".into(), "ruby".into());
173
+ map.insert("wrapper_version".into(), CRATE_VERSION.into());
174
+ map
175
+ })
176
+ .build()
177
+ .map_err(|e| {
178
+ let exception = AnyException::new("ExogressError", Some(e.to_string().as_str()));
179
+ VM::raise_ex(exception);
180
+ })
181
+ .unwrap();
182
+
183
+ let (reload_config_tx, reload_config_rx) = mpsc::unbounded();
184
+ let (stop_tx, stop_rx) = oneshot::channel();
185
+
186
+ let instance = RustInstance {
187
+ client: parking_lot::Mutex::new(Some(client)),
188
+ reload_config_tx: parking_lot::Mutex::new(reload_config_tx),
189
+ reload_config_rx: Arc::new(parking_lot::Mutex::new(Some(reload_config_rx))),
190
+ stop_tx: parking_lot::Mutex::new(Some(stop_tx)),
191
+ stop_rx: Arc::new(parking_lot::Mutex::new(Some(stop_rx))),
192
+ };
193
+
194
+ Class::from_existing("Instance").wrap_data(instance, &*INSTANCE_WRAPPER)
195
+ }
196
+
197
+ fn spawn() -> NilClass {
198
+ let inner = itself.get_data(&*INSTANCE_WRAPPER);
199
+
200
+ let rt = Runtime::new().map_err(|e| {
201
+ let exception = AnyException::new("ExogressError", Some(e.to_string().as_str()));
202
+ VM::raise_ex(exception);
203
+ })
204
+ .unwrap();
205
+
206
+ let resolver = TokioAsyncResolver::from_system_conf(TokioHandle)
207
+ .map_err(|e| {
208
+ let exception = AnyException::new("ExogressError", Some(e.to_string().as_str()));
209
+ VM::raise_ex(exception);
210
+ })
211
+ .unwrap();
212
+
213
+
214
+ // let stop_rx = inner
215
+ // .stop_rx
216
+ // .lock()
217
+ // .take()
218
+ // .ok_or_else(|| {
219
+ // let exception = AnyException::new("ExogressError", Some("instance has already been spawned"));
220
+ // VM::raise_ex(exception);
221
+ // })
222
+ // .unwrap();
223
+
224
+ let work = || {
225
+ let resolver = resolver.clone();
226
+ let reload_config_tx = inner.reload_config_tx.lock().clone();
227
+ let reload_config_rx = inner.reload_config_rx.clone();
228
+ let stop_rx = inner.stop_rx.clone();
229
+
230
+ rt.block_on(async move {
231
+ println!("Spawn block_on");
232
+ if let (Some(client), Some(reload_config_rx), Some(stop_rx)) = (inner.client.lock().take(), reload_config_rx.lock().take(), stop_rx.lock().take()) {
233
+ let spawn = client.spawn(reload_config_tx.clone(), reload_config_rx, resolver);
234
+
235
+ tokio::select! {
236
+ r = spawn => {
237
+ println!("spawn stopped");
238
+ if let Err(e) = r {
239
+ return Err(anyhow::anyhow!(e.to_string()));
240
+ }
241
+ },
242
+ _ = stop_rx => {
243
+ println!("stop by request");
244
+ // info!("stop exogress instance by request");
245
+ }
246
+ }
247
+ } else {
248
+ return Err(anyhow::anyhow!("instance has already been spawned"));
249
+ }
250
+
251
+ Ok(())
252
+ })
253
+ };
254
+
255
+ let unblocking_function = || {};
256
+
257
+ let result = Thread::call_without_gvl(
258
+ work,
259
+ Some(unblocking_function)
260
+ );
261
+
262
+ result
263
+ .map_err(|e| {
264
+ let exception = AnyException::new("ExogressError", Some(e.to_string().as_str()));
265
+ VM::raise_ex(exception);
266
+ })
267
+ .unwrap();
268
+
269
+ NilClass::new()
270
+ }
271
+
272
+
273
+ fn reload() -> NilClass {
274
+ let inner = itself.get_data(&*INSTANCE_WRAPPER);
275
+
276
+ inner.reload_config_tx
277
+ .lock()
278
+ .unbounded_send(())
279
+ .map_err(|e| {
280
+ let exception = AnyException::new("ExogressError", Some(format!("failed to send reload request: {}", e).as_str()));
281
+ VM::raise_ex(exception);
282
+ })
283
+ .unwrap();
284
+
285
+ NilClass::new()
286
+ }
287
+
288
+ fn stop() -> NilClass {
289
+ let inner = itself.get_data(&*INSTANCE_WRAPPER);
290
+
291
+ inner.stop_tx
292
+ .lock()
293
+ .take()
294
+ .ok_or_else(|| {
295
+ let exception = AnyException::new("ExogressError", Some("instance already stopped"));
296
+ VM::raise_ex(exception)
297
+ })
298
+ .unwrap()
299
+ .send(())
300
+ .map_err(|_| {
301
+ let exception = AnyException::new("ExogressError", Some("failed to send reload request"));
302
+ VM::raise_ex(exception)
303
+ })
304
+ .unwrap();
305
+
306
+ NilClass::new()
307
+ }
308
+ );
data/src/lib.rs ADDED
@@ -0,0 +1,17 @@
1
+ #[macro_use]
2
+ extern crate rutie;
3
+
4
+ use rutie::{Class, Object, RString, VM};
5
+
6
+ mod instance;
7
+
8
+ #[allow(non_snake_case)]
9
+ #[no_mangle]
10
+ pub extern "C" fn Init_rutie_exogress() {
11
+ Class::new("Instance", None).define(|klass| {
12
+ klass.def_self("new", instance::new);
13
+ klass.def("spawn", instance::spawn);
14
+ klass.def("reload", instance::reload);
15
+ klass.def("stop", instance::stop);
16
+ });
17
+ }
metadata ADDED
@@ -0,0 +1,110 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: exogress
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.1.pre.alpha.1
5
+ platform: ruby
6
+ authors:
7
+ - Exogress Team
8
+ autorequire:
9
+ bindir: exe
10
+ cert_chain: []
11
+ date: 2021-07-06 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: rutie
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - "~>"
18
+ - !ruby/object:Gem::Version
19
+ version: 0.0.4
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - "~>"
25
+ - !ruby/object:Gem::Version
26
+ version: 0.0.4
27
+ - !ruby/object:Gem::Dependency
28
+ name: bundler
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
32
+ - !ruby/object:Gem::Version
33
+ version: '0'
34
+ type: :development
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ - !ruby/object:Gem::Dependency
42
+ name: rake
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - "~>"
46
+ - !ruby/object:Gem::Version
47
+ version: '10.0'
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - "~>"
53
+ - !ruby/object:Gem::Version
54
+ version: '10.0'
55
+ description: Exogress is an edge network built for your cloud
56
+ email:
57
+ - team@exogress.com
58
+ executables: []
59
+ extensions:
60
+ - Rakefile
61
+ extra_rdoc_files: []
62
+ files:
63
+ - ".github/workflows/main.yml"
64
+ - ".gitignore"
65
+ - ".idea/.gitignore"
66
+ - ".idea/exogress-ruby.iml"
67
+ - ".idea/modules.xml"
68
+ - ".idea/vcs.xml"
69
+ - ".rspec"
70
+ - Cargo.toml
71
+ - Exofile.yml
72
+ - Gemfile
73
+ - Gemfile.lock
74
+ - LICENSE.txt
75
+ - README.md
76
+ - Rakefile
77
+ - bin/console
78
+ - bin/setup
79
+ - example/example.rb
80
+ - exogress.gemspec
81
+ - lib/exogress.rb
82
+ - lib/exogress/version.rb
83
+ - src/instance.rs
84
+ - src/lib.rs
85
+ homepage: https://exogess.com
86
+ licenses:
87
+ - Apache 2.0
88
+ metadata:
89
+ homepage_uri: https://exogess.com
90
+ source_code_uri: https://github.com/exogress/exogress-ruby
91
+ post_install_message:
92
+ rdoc_options: []
93
+ require_paths:
94
+ - lib
95
+ required_ruby_version: !ruby/object:Gem::Requirement
96
+ requirements:
97
+ - - ">="
98
+ - !ruby/object:Gem::Version
99
+ version: 2.4.0
100
+ required_rubygems_version: !ruby/object:Gem::Requirement
101
+ requirements:
102
+ - - ">"
103
+ - !ruby/object:Gem::Version
104
+ version: 1.3.1
105
+ requirements: []
106
+ rubygems_version: 3.2.15
107
+ signing_key:
108
+ specification_version: 4
109
+ summary: Exogress client for Ruby
110
+ test_files: []