stability_sdk 0.2.11 → 0.2.12

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 431d7a70dc0a5a538abdbe9a486bf5c632d1e6a8e7e58dd7fedf1fa89b15722b
4
- data.tar.gz: a6d5c05cf4915e7c91ceeb92864b2cc84f852ec40a61ce174ba57b3a97ec0df9
3
+ metadata.gz: d5aac33cb8d504aab26b515dc2fa6bd9d76c70829a0aa706eabc6be39043b143
4
+ data.tar.gz: ca6a3cd1cd24763a9f9427132a4e8fde4c688d9bc9d3409ef921139fa62fa232
5
5
  SHA512:
6
- metadata.gz: 7c5ba5862fd6446e243cdf54760fe596a4298e2d2860183df4cef847cc75d4414e9ceb21e8bd927e71e0fbacca9ce742628107197ca1e7c380abbbabff1e7cdc
7
- data.tar.gz: 69b3cef394cbd5bd784bfd8953b1bd8721e4921e96f3a7bda79c0de3a733692853005008e1946cad75b24889df5dc1c8f9479238baac488a37a64ef49dbe39b7
6
+ metadata.gz: 95b76f6caf8e5a32af792cc0d284f81b76c7e38c682b24a5fc91204b3373096a47a98ab1ee6f0e32cbbd2039ad6b57c920c262661cda221c54eac529bd54e51a
7
+ data.tar.gz: f196c8b879b36e69c84d40c2528fd9fbf7f07e1ae6eec9c4a996a66a8a73841ea50d73d8ca941b7813ca9d5fbada94140143619bdb841de4ce9f71316af1303e
data/README.md CHANGED
@@ -61,9 +61,25 @@ Options:
61
61
  -m, --mask_image=VAL path to mask image
62
62
  --start_schedule=VAL start schedule for init image (must be greater than 0, 1 is full strength text prompt, no trace of image). default 1.0
63
63
  --end_schedule=VAL end schedule for init image. default 0.01
64
+ --guidance_preset=VAL Guidance preset to use. See generation.GuidancePreset for supported values. default `GUIDANCE_PRESET_NONE`
65
+ --guidance_cuts=VAL Number of cuts to use for guidance. default 0
66
+ --guidance_strength=VAL Strength of the guidance. We recommend values in range [0.0,1.0]. A good default is 0.25. default nil
67
+ --guidance_prompt=VAL Prompt to use for guidance, defaults to `YOUR_PROMPT_TEXT` argument (above) if not specified.
68
+ --guidance_models=VAL Models to use for guidance. default nil
64
69
  -v, --verbose
65
70
  ```
66
71
 
72
+ #### CLIP guidance
73
+
74
+ By specifying `--guidance_preset` and other `--guidance_*` options, you can use CLIP guidance, which is enabled by default on DreamStudio's web interface.
75
+ See also [this notebook](https://github.com/Stability-AI/stability-sdk/blob/c04381f960008f37c7392467cfaabfdf8f763e6a/nbs/demo_colab.ipynb) for more details.
76
+
77
+ ```sh
78
+ # example
79
+ # [note] --steps=35 is recommended. which is also the default value of the web interface
80
+ STABILITY_SDK_API_KEY=xxx stability-client --guidance_preset=GUIDANCE_PRESET_FAST_BLUE --guidance_strength=0.25 --steps=35 --sampler=k_dpm_2_ancestral "A dream of a distant galaxy, by Caspar David Friedrich, matte painting trending on artstation HQ"
81
+ ```
82
+
67
83
  ### SDK usage
68
84
 
69
85
  This sample code saves a generated image as `result.png`.
@@ -116,6 +132,32 @@ After checking out the repo, run `bin/setup` to install dependencies. Then, run
116
132
 
117
133
  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 tags, and push the `.gem` file to [rubygems.org](https://rubygems.org).
118
134
 
135
+ ### update submodule to try a new feature on Stability-AI/api-interfaces
136
+
137
+ - update submodule
138
+
139
+ ```sh
140
+ git submodule update --init # if you haven't fetched the content of the submodule yet
141
+ cd api-interfaces
142
+
143
+ # checkout some branch/commit you need
144
+ git fetch
145
+ git reset --hard origin/some_branch
146
+
147
+ cd ..
148
+ ```
149
+
150
+ - build
151
+
152
+ ```sh
153
+ bundle exec rake protoc
154
+
155
+ git diff
156
+ # now you may be able to confirm that the diff is created in lib/generation_pb.rb
157
+ ```
158
+
159
+ - modify the `lib/stability_sdk/client.rb` to try some new features
160
+
119
161
  ## Contributing
120
162
 
121
163
  Bug reports and pull requests are welcome on GitHub at https://github.com/cou929/stability-sdk-ruby.
data/exe/stability-client CHANGED
@@ -18,20 +18,25 @@ opt.banner = "Usage: stability-client [options] YOUR_PROMPT_TEXT"
18
18
  opt.separator ""
19
19
  opt.separator "Options:"
20
20
  opt.on("--api_key=VAL", "api key of DreamStudio account. You can also specify by a STABILITY_SDK_API_KEY environment variable") {|v| options[:api_key] = v }
21
- opt.on("-H", "--height=VAL", "height of image in pixel. default 512") {|v| options[:height] = v }
22
- opt.on("-W", "--width=VAL", "width of image in pixel. default 512") {|v| options[:width] = v }
23
- opt.on("-C", "--cfg_scale=VAL", "CFG scale factor. default 7.0") {|v| options[:cfg_scale] = v }
24
- opt.on("-A", "--sampler=VAL", "ddim, plms, k_euler, k_euler_ancestral, k_heun, k_dpm_2, k_dpm_2_ancestral, k_lms. default k_lms") {|v| options[:sampler] = v }
25
- opt.on("-s", "--steps=VAL", "number of steps. default 50") {|v| options[:steps] = v }
26
- opt.on("-S", "--seed=VAL", "random seed to use in integer") {|v| options[:seed] = v }
27
- opt.on("-p", "--prefix=VAL", "output prefixes for artifacts. default `generation`") {|v| options[:prefix] = v }
21
+ opt.on("-H", "--height=VAL", Integer, "height of image in pixel. default 512") {|v| options[:height] = v }
22
+ opt.on("-W", "--width=VAL", Integer, "width of image in pixel. default 512") {|v| options[:width] = v }
23
+ opt.on("-C", "--cfg_scale=VAL", Float, "CFG scale factor. default 7.0") {|v| options[:cfg_scale] = v }
24
+ opt.on("-A", "--sampler=VAL", String, "ddim, plms, k_euler, k_euler_ancestral, k_heun, k_dpm_2, k_dpm_2_ancestral, k_lms. default k_lms") {|v| options[:sampler] = v }
25
+ opt.on("-s", "--steps=VAL", Integer, "number of steps. default 50") {|v| options[:steps] = v }
26
+ opt.on("-S", "--seed=VAL", Integer, "random seed to use in integer") {|v| options[:seed] = v }
27
+ opt.on("-p", "--prefix=VAL", String, "output prefixes for artifacts. default `generation`") {|v| options[:prefix] = v }
28
28
  opt.on("--no-store", "do not write out artifacts") {|v| options[:no_store] = v }
29
- opt.on("-n", "--num_samples=VAL", "number of samples to generate") {|v| options[:num_samples] = v }
30
- opt.on("-e", "--engine=VAL", "engine to use for inference. default `stable-diffusion-v1`") {|v| options[:engine_id] = v }
31
- opt.on("-i", "--init_image=VAL", "path to init image") {|v| options[:init_image] = v }
32
- opt.on("-m", "--mask_image=VAL", "path to mask image") {|v| options[:mask_image] = v }
33
- opt.on("--start_schedule=VAL", "start schedule for init image (must be greater than 0, 1 is full strength text prompt, no trace of image). default 1.0") {|v| options[:start_schedule] = v }
34
- opt.on("--end_schedule=VAL", "end schedule for init image. default 0.01") {|v| options[:end_schedule] = v }
29
+ opt.on("-n", "--num_samples=VAL", Integer, "number of samples to generate. default 1") {|v| options[:num_samples] = v }
30
+ opt.on("-e", "--engine=VAL", String, "engine to use for inference. default `stable-diffusion-v1-5`") {|v| options[:engine_id] = v }
31
+ opt.on("-i", "--init_image=VAL", String, "path to init image") {|v| options[:init_image] = v }
32
+ opt.on("-m", "--mask_image=VAL", String, "path to mask image") {|v| options[:mask_image] = v }
33
+ opt.on("--start_schedule=VAL", Float, "start schedule for init image (must be greater than 0, 1 is full strength text prompt, no trace of image). default 1.0") {|v| options[:start_schedule] = v }
34
+ opt.on("--end_schedule=VAL", Float, "end schedule for init image. default 0.01") {|v| options[:end_schedule] = v }
35
+ opt.on("--guidance_preset=VAL", String,"Guidance preset to use. See generation.GuidancePreset for supported values. default `GUIDANCE_PRESET_NONE`") {|v| options[:guidance_preset] = v }
36
+ opt.on("--guidance_cuts=VAL", Integer, "Number of cuts to use for guidance. default 0") {|v| options[:guidance_cuts] = v }
37
+ opt.on("--guidance_strength=VAL", Float, "Strength of the guidance. We recommend values in range [0.0,1.0]. A good default is 0.25. default nil") {|v| options[:guidance_strength] = v }
38
+ opt.on("--guidance_prompt=VAL", String, "Prompt to use for guidance, defaults to `YOUR_PROMPT_TEXT` argument (above) if not specified.") {|v| options[:guidance_prompt] = v }
39
+ opt.on("--guidance_models=VAL", Array, "Models to use for guidance. default nil") {|v| options[:guidance_models] = v }
35
40
  opt.on("-v", "--verbose") { logger.level = Logger::DEBUG }
36
41
  opt.parse!(ARGV)
37
42
 
@@ -48,7 +53,7 @@ if options.has_key?(:init_image)
48
53
  raise StabilitySDK::InvalidParameter, "width and height of init_image must be a multiple of 64" if size[0] % 64 != 0 || size[1] % 64 != 0
49
54
  end
50
55
 
51
- client = StabilitySDK::Client.new(api_key: options[:api_key])
56
+ client = StabilitySDK::Client.new(api_key: options[:api_key], logger: logger)
52
57
 
53
58
  client.generate(prompt, options) do |answer|
54
59
  StabilitySDK::CLI.save_answer(answer, options, logger)
@@ -23,10 +23,15 @@ module StabilitySDK
23
23
  logger.warn "not implemented for ArtifactType #{artifact.type}"
24
24
  end
25
25
 
26
+ if artifact.finish_reason == :FILTER
27
+ logger.debug "the generated image is filtered"
28
+ end
29
+
26
30
  next if filename == "" || contents == ""
27
31
 
28
32
  File.open(filename, "wb") do |f|
29
33
  f.write(contents)
34
+ logger.debug "wrote #{artifact.type} to #{filename}"
30
35
  end
31
36
  end
32
37
  end
@@ -1,5 +1,6 @@
1
1
  require "grpc"
2
2
  require "generation_services_pb"
3
+ require "logger"
3
4
 
4
5
  module StabilitySDK
5
6
  class Client
@@ -36,29 +37,37 @@ module StabilitySDK
36
37
  stub_params[kw] = options[kw] if options.has_key?(kw)
37
38
  end
38
39
 
40
+ if options.has_key?(:logger)
41
+ @logger = options[:logger]
42
+ else
43
+ logger = Logger.new(STDOUT)
44
+ logger.level = Logger::WARN
45
+ @logger = logger
46
+ end
47
+
39
48
  @stub = Gooseai::GenerationService::Stub.new(host, creds, **stub_params)
40
49
  end
41
50
 
42
51
  def generate(prompt, options, &block)
43
- width = options.has_key?(:width) ? options[:width].to_i : DEFAULT_IMAGE_WIDTH
44
- height = options.has_key?(:height) ? options[:height].to_i : DEFAULT_IMAGE_HEIGHT
52
+ width = options.has_key?(:width) ? options[:width] : DEFAULT_IMAGE_WIDTH
53
+ height = options.has_key?(:height) ? options[:height] : DEFAULT_IMAGE_HEIGHT
45
54
 
46
55
  if width % 64 != 0 || height % 64 != 0
47
56
  raise InvalidParameter, "width and height must be a multiple of 64"
48
57
  end
49
58
 
50
- samples = options.has_key?(:num_samples) ? options[:num_samples].to_i : DEFAULT_SAMPLE_SIZE
51
- steps = options.has_key?(:steps) ? options[:steps].to_i : DEFAULT_STEPS
52
- seed = options.has_key?(:seed) ? [options[:seed].to_i] : [rand(4294967295)]
59
+ samples = options.has_key?(:num_samples) ? options[:num_samples] : DEFAULT_SAMPLE_SIZE
60
+ steps = options.has_key?(:steps) ? options[:steps] : DEFAULT_STEPS
61
+ seed = options.has_key?(:seed) ? [options[:seed]] : [rand(4294967295)]
53
62
  transform = Gooseai::TransformType.new(
54
- diffusion: options.has_key?(:sampler) ? SAMPLER_ALGORITHMS[options[:sampler]] : DEFAULT_SAMPLER_ALGORITHM,
63
+ diffusion: options.has_key?(:sampler) ? SAMPLER_ALGORITHMS[options[:sampler].to_sym] : DEFAULT_SAMPLER_ALGORITHM,
55
64
  )
56
- parameters = [Gooseai::StepParameter.new(
65
+ step_parameter = Gooseai::StepParameter.new(
57
66
  scaled_step: 0,
58
67
  sampler: Gooseai::SamplerParameters.new(
59
- cfg_scale: options.has_key?(:cfg_scale) ? options[:cfg_scale].to_f : DEFAULT_CFG_SCALE,
68
+ cfg_scale: options.has_key?(:cfg_scale) ? options[:cfg_scale] : DEFAULT_CFG_SCALE,
60
69
  ),
61
- )]
70
+ )
62
71
 
63
72
  prompt_param = []
64
73
  if prompt != ""
@@ -66,21 +75,65 @@ module StabilitySDK
66
75
  end
67
76
  if options.has_key?(:init_image)
68
77
  prompt_param << init_image_to_prompt(options[:init_image])
69
- parameters = [Gooseai::StepParameter.new(
70
- scaled_step: 0,
71
- sampler: Gooseai::SamplerParameters.new(
72
- cfg_scale: options.has_key?(:cfg_scale) ? options[:cfg_scale].to_f : DEFAULT_CFG_SCALE,
73
- ),
74
- schedule: Gooseai::ScheduleParameters.new(
75
- start: options.has_key?(:start_schedule) ? options[:start_schedule].to_f : DEFAULT_START_SCHEDULE,
76
- end: options.has_key?(:end_schedule) ? options[:end_schedule].to_f : DEFAULT_END_SCHEDULE,
77
- ),
78
- )]
78
+ step_parameter.scaled_step = 0
79
+ step_parameter.sampler = Gooseai::SamplerParameters.new(
80
+ cfg_scale: options.has_key?(:cfg_scale) ? options[:cfg_scale] : DEFAULT_CFG_SCALE,
81
+ )
82
+ step_parameter.schedule = Gooseai::ScheduleParameters.new(
83
+ start: options.has_key?(:start_schedule) ? options[:start_schedule] : DEFAULT_START_SCHEDULE,
84
+ end: options.has_key?(:end_schedule) ? options[:end_schedule] : DEFAULT_END_SCHEDULE,
85
+ )
79
86
  end
80
87
  if options.has_key?(:mask_image)
81
88
  prompt_param << mask_image_to_prompt(options[:mask_image])
82
89
  end
83
90
 
91
+ # CLIP guidance
92
+ if options.has_key?(:guidance_preset) && options[:guidance_preset] != "GUIDANCE_PRESET_NONE"
93
+ step_parameter.sampler = nil
94
+
95
+ guidance_prompt =
96
+ if options.has_key?(:guidance_prompt)
97
+ Gooseai::Prompt.new(text: options[:guidance_prompt])
98
+ else
99
+ Gooseai::Prompt.new(text: prompt)
100
+ end
101
+
102
+ guidance_strength = nil
103
+ if options.has_key?(:guidance_strength) && options[:guidance_strength] != 0
104
+ guidance_strength = options[:guidance_strength]
105
+ end
106
+
107
+ models = nil
108
+ if options.has_key?(:guidance_models)
109
+ models = options[:guidance_models].map { |m| Gooseai::Model.new(alias: m) }
110
+ end
111
+
112
+ cutouts = nil
113
+ if options.has_key?(:guidance_cuts)
114
+ cutouts = Gooseai::CutoutParameters.new(count: options[:guidance_cuts])
115
+ end
116
+
117
+ step_parameter.guidance = Gooseai::GuidanceParameters.new(
118
+ guidance_preset: Gooseai::GuidancePreset.const_get(options[:guidance_preset].to_sym),
119
+ instances: [
120
+ Gooseai::GuidanceInstanceParameters.new(
121
+ guidance_strength: guidance_strength,
122
+ models: models,
123
+ cutouts: cutouts,
124
+ prompt: guidance_prompt,
125
+ ),
126
+ ],
127
+ )
128
+
129
+ if transform.diffusion != Gooseai::DiffusionSampler::SAMPLER_K_DPM_2_ANCESTRAL && transform.diffusion != Gooseai::DiffusionSampler::SAMPLER_K_EULER_ANCESTRAL
130
+ transform = Gooseai::TransformType.new(
131
+ diffusion: Gooseai::DiffusionSampler::SAMPLER_K_DPM_2_ANCESTRAL
132
+ )
133
+ @logger.warn "CLIP guidance is only supported with ancestral samplers. So override it with SAMPLER_K_DPM_2_ANCESTRAL."
134
+ end
135
+ end
136
+
84
137
  image_param = Gooseai::ImageParameters.new(
85
138
  width: width,
86
139
  height: height,
@@ -88,7 +141,7 @@ module StabilitySDK
88
141
  steps: steps,
89
142
  seed: seed,
90
143
  transform: transform,
91
- parameters: parameters,
144
+ parameters: [step_parameter],
92
145
  )
93
146
 
94
147
  req = Gooseai::Request.new(
@@ -97,8 +150,20 @@ module StabilitySDK
97
150
  image: image_param
98
151
  )
99
152
 
153
+ @logger.debug "sending request."
154
+ start = Time.now
100
155
  @stub.generate(req).each do |answer|
156
+ duration = Time.now - start
157
+ if answer.artifacts.size > 0
158
+ artifact_types = answer.artifacts.map { |a| a.type }
159
+ @logger.debug "got #{answer.answer_id} with #{artifact_types} in #{duration.round(2)}s"
160
+ else
161
+ @logger.debug "got keepalive #{answer.answer_id} in #{duration.round(2)}s"
162
+ end
163
+
101
164
  block.call(answer)
165
+
166
+ start = Time.now
102
167
  end
103
168
  end
104
169
 
@@ -1,3 +1,3 @@
1
1
  module StabilitySDK
2
- VERSION = "0.2.11"
2
+ VERSION = "0.2.12"
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: stability_sdk
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.11
4
+ version: 0.2.12
5
5
  platform: ruby
6
6
  authors:
7
7
  - Kosei Moriyama
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2022-10-28 00:00:00.000000000 Z
11
+ date: 2022-10-31 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: grpc