langsmithrb_rails 0.1.0 → 0.1.1
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/.rspec +3 -0
- data/.rspec_status +82 -0
- data/CHANGELOG.md +25 -0
- data/Gemfile +20 -0
- data/Gemfile.lock +321 -0
- data/LICENSE +21 -0
- data/README.md +268 -0
- data/Rakefile +10 -0
- data/langsmithrb_rails-0.1.0.gem +0 -0
- data/langsmithrb_rails.gemspec +45 -0
- data/lib/generators/langsmithrb_rails/buffer/buffer_generator.rb +94 -0
- data/lib/generators/langsmithrb_rails/buffer/templates/create_langsmith_run_buffers.rb +29 -0
- data/lib/generators/langsmithrb_rails/buffer/templates/flush_buffer_job.rb +40 -0
- data/lib/generators/langsmithrb_rails/buffer/templates/langsmith.rake +71 -0
- data/lib/generators/langsmithrb_rails/buffer/templates/langsmith_run_buffer.rb +70 -0
- data/lib/generators/langsmithrb_rails/buffer/templates/migration.rb +28 -0
- data/lib/generators/langsmithrb_rails/ci/ci_generator.rb +37 -0
- data/lib/generators/langsmithrb_rails/ci/templates/langsmith-evals.yml +85 -0
- data/lib/generators/langsmithrb_rails/ci/templates/langsmith_export_summary.rb +81 -0
- data/lib/generators/langsmithrb_rails/demo/demo_generator.rb +81 -0
- data/lib/generators/langsmithrb_rails/demo/templates/chat_controller.js +88 -0
- data/lib/generators/langsmithrb_rails/demo/templates/chat_controller.rb +58 -0
- data/lib/generators/langsmithrb_rails/demo/templates/chat_message.rb +24 -0
- data/lib/generators/langsmithrb_rails/demo/templates/create_chat_messages.rb +19 -0
- data/lib/generators/langsmithrb_rails/demo/templates/index.html.erb +180 -0
- data/lib/generators/langsmithrb_rails/demo/templates/llm_service.rb +165 -0
- data/lib/generators/langsmithrb_rails/evals/evals_generator.rb +52 -0
- data/lib/generators/langsmithrb_rails/evals/templates/checks/correctness.rb +71 -0
- data/lib/generators/langsmithrb_rails/evals/templates/checks/llm_graded.rb +137 -0
- data/lib/generators/langsmithrb_rails/evals/templates/datasets/sample.yml +60 -0
- data/lib/generators/langsmithrb_rails/evals/templates/langsmith_evals.rake +255 -0
- data/lib/generators/langsmithrb_rails/evals/templates/targets/http.rb +120 -0
- data/lib/generators/langsmithrb_rails/evals/templates/targets/ruby.rb +136 -0
- data/lib/generators/langsmithrb_rails/install/install_generator.rb +35 -0
- data/lib/generators/langsmithrb_rails/install/templates/config.yml +45 -0
- data/lib/generators/langsmithrb_rails/install/templates/initializer.rb +34 -0
- data/lib/generators/langsmithrb_rails/privacy/privacy_generator.rb +39 -0
- data/lib/generators/langsmithrb_rails/privacy/templates/custom_redactor.rb +132 -0
- data/lib/generators/langsmithrb_rails/privacy/templates/privacy.yml +88 -0
- data/lib/generators/langsmithrb_rails/privacy/templates/privacy_initializer.rb +41 -0
- data/lib/generators/langsmithrb_rails/tracing/templates/langsmith_traced.rb +146 -0
- data/lib/generators/langsmithrb_rails/tracing/templates/langsmith_traced_job.rb +151 -0
- data/lib/generators/langsmithrb_rails/tracing/templates/request_tracing.rb +117 -0
- data/lib/generators/langsmithrb_rails/tracing/tracing_generator.rb +78 -0
- data/lib/langsmithrb_rails/client.rb +77 -0
- data/lib/langsmithrb_rails/config.rb +72 -0
- data/lib/langsmithrb_rails/generators/langsmithrb_rails/langsmith_generator.rb +61 -0
- data/lib/langsmithrb_rails/generators/langsmithrb_rails/templates/langsmith_initializer.rb +22 -0
- data/lib/langsmithrb_rails/langsmith.rb +35 -0
- data/lib/langsmithrb_rails/railtie.rb +33 -0
- data/lib/langsmithrb_rails/redactor.rb +76 -0
- data/lib/langsmithrb_rails/version.rb +5 -0
- data/lib/langsmithrb_rails.rb +31 -0
- metadata +59 -6
@@ -0,0 +1,78 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module LangsmithrbRails
|
4
|
+
module Generators
|
5
|
+
# Generator for adding LangSmith tracing to Rails applications
|
6
|
+
class TracingGenerator < Rails::Generators::Base
|
7
|
+
source_root File.expand_path("templates", __dir__)
|
8
|
+
|
9
|
+
desc "Adds LangSmith tracing to your Rails application"
|
10
|
+
|
11
|
+
def create_middleware
|
12
|
+
template "request_tracing.rb", "app/middleware/langsmithrb_rails/request_tracing.rb"
|
13
|
+
end
|
14
|
+
|
15
|
+
def create_service_concern
|
16
|
+
template "langsmith_traced.rb", "app/services/concerns/langsmith_traced.rb"
|
17
|
+
end
|
18
|
+
|
19
|
+
def create_job_concern
|
20
|
+
template "langsmith_traced_job.rb", "app/jobs/concerns/langsmith_traced_job.rb"
|
21
|
+
end
|
22
|
+
|
23
|
+
def update_application_config
|
24
|
+
application_rb_path = "config/application.rb"
|
25
|
+
|
26
|
+
if File.exist?(application_rb_path)
|
27
|
+
middleware_line = " config.middleware.use LangsmithrbRails::RequestTracing"
|
28
|
+
|
29
|
+
# Check if middleware is already configured
|
30
|
+
if File.read(application_rb_path).include?(middleware_line)
|
31
|
+
say_status :skip, "Middleware already configured in application.rb", :yellow
|
32
|
+
else
|
33
|
+
# Find the class Application < Rails::Application line
|
34
|
+
application_content = File.read(application_rb_path)
|
35
|
+
|
36
|
+
if application_content =~ /class Application < Rails::Application/
|
37
|
+
inject_into_file application_rb_path, after: "class Application < Rails::Application\n" do
|
38
|
+
<<~RUBY
|
39
|
+
# Use LangSmith request tracing middleware
|
40
|
+
#{middleware_line}
|
41
|
+
|
42
|
+
RUBY
|
43
|
+
end
|
44
|
+
|
45
|
+
say_status :insert, "Added middleware to application.rb", :green
|
46
|
+
else
|
47
|
+
say_status :error, "Could not find the Application class in application.rb", :red
|
48
|
+
end
|
49
|
+
end
|
50
|
+
else
|
51
|
+
say_status :error, "Could not find application.rb", :red
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
def create_directories
|
56
|
+
empty_directory "app/middleware/langsmithrb_rails"
|
57
|
+
empty_directory "app/services/concerns"
|
58
|
+
empty_directory "app/jobs/concerns"
|
59
|
+
end
|
60
|
+
|
61
|
+
def display_post_install_message
|
62
|
+
say "\n"
|
63
|
+
say "LangSmith tracing has been added to your Rails application! 🎉", :green
|
64
|
+
say "\n"
|
65
|
+
say "Usage:", :yellow
|
66
|
+
say " 1. Use the LangsmithTraced concern in your services:", :yellow
|
67
|
+
say " include LangsmithTraced", :yellow
|
68
|
+
say " LangsmithTraced.trace(name: 'my_operation', type: 'llm') { ... }", :yellow
|
69
|
+
say " 2. Use the LangsmithTracedJob concern in your jobs:", :yellow
|
70
|
+
say " include LangsmithTracedJob", :yellow
|
71
|
+
say "\n"
|
72
|
+
say "To add a local buffer for traces, run:", :yellow
|
73
|
+
say " bin/rails g langsmithrb_rails:buffer", :yellow
|
74
|
+
say "\n"
|
75
|
+
end
|
76
|
+
end
|
77
|
+
end
|
78
|
+
end
|
@@ -0,0 +1,77 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "net/http"
|
4
|
+
require "json"
|
5
|
+
require "uri"
|
6
|
+
|
7
|
+
module LangsmithrbRails
|
8
|
+
# Direct REST client for LangSmith API
|
9
|
+
class Client
|
10
|
+
# Initialize a new LangSmith client
|
11
|
+
# @param api_key [String] LangSmith API key
|
12
|
+
# @param api_url [String] LangSmith API URL
|
13
|
+
def initialize(api_key: Config[:api_key], api_url: Config[:api_url])
|
14
|
+
@api_key = api_key
|
15
|
+
@api_url = api_url.chomp("/")
|
16
|
+
end
|
17
|
+
|
18
|
+
# Create a new run in LangSmith
|
19
|
+
# @param payload [Hash] Run data
|
20
|
+
# @return [Hash] Response with status and body
|
21
|
+
def create_run(payload)
|
22
|
+
post("/runs", payload)
|
23
|
+
end
|
24
|
+
|
25
|
+
# Update an existing run in LangSmith
|
26
|
+
# @param id [String] Run ID
|
27
|
+
# @param payload [Hash] Updated run data
|
28
|
+
# @return [Hash] Response with status and body
|
29
|
+
def update_run(id, payload)
|
30
|
+
patch("/runs/#{id}", payload)
|
31
|
+
end
|
32
|
+
|
33
|
+
private
|
34
|
+
|
35
|
+
# Make a POST request
|
36
|
+
# @param path [String] API path
|
37
|
+
# @param payload [Hash] Request payload
|
38
|
+
# @return [Hash] Response with status and body
|
39
|
+
def post(path, payload)
|
40
|
+
request(Net::HTTP::Post, path, payload)
|
41
|
+
end
|
42
|
+
|
43
|
+
# Make a PATCH request
|
44
|
+
# @param path [String] API path
|
45
|
+
# @param payload [Hash] Request payload
|
46
|
+
# @return [Hash] Response with status and body
|
47
|
+
def patch(path, payload)
|
48
|
+
request(Net::HTTP::Patch, path, payload)
|
49
|
+
end
|
50
|
+
|
51
|
+
# Make an HTTP request
|
52
|
+
# @param klass [Class] Net::HTTP request class
|
53
|
+
# @param path [String] API path
|
54
|
+
# @param payload [Hash] Request payload
|
55
|
+
# @return [Hash] Response with status and body
|
56
|
+
def request(klass, path, payload)
|
57
|
+
uri = URI.parse("#{@api_url}#{path}")
|
58
|
+
http = Net::HTTP.new(uri.host, uri.port)
|
59
|
+
http.use_ssl = uri.scheme == "https"
|
60
|
+
http.open_timeout = Config[:open_timeout_seconds]
|
61
|
+
http.read_timeout = Config[:timeout_seconds]
|
62
|
+
|
63
|
+
req = klass.new(uri.request_uri)
|
64
|
+
req["Authorization"] = "Bearer #{@api_key}" if @api_key
|
65
|
+
req["Content-Type"] = "application/json"
|
66
|
+
req.body = JSON.generate(payload)
|
67
|
+
|
68
|
+
res = http.request(req)
|
69
|
+
{
|
70
|
+
status: res.code.to_i,
|
71
|
+
body: (JSON.parse(res.body) rescue { "raw" => res.body })
|
72
|
+
}
|
73
|
+
rescue => e
|
74
|
+
{ status: 0, error: e.message }
|
75
|
+
end
|
76
|
+
end
|
77
|
+
end
|
@@ -0,0 +1,72 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "yaml"
|
4
|
+
require "ostruct"
|
5
|
+
|
6
|
+
module LangsmithrbRails
|
7
|
+
# Configuration class for LangsmithrbRails
|
8
|
+
class Config
|
9
|
+
# Default configuration values
|
10
|
+
DEFAULTS = {
|
11
|
+
api_url: "https://api.smith.langchain.com",
|
12
|
+
project: nil,
|
13
|
+
api_key: ENV["LANGSMITH_API_KEY"],
|
14
|
+
sampling_rate: ENV.fetch("LANGSMITH_SAMPLING", "0.1").to_f,
|
15
|
+
redact_by_default: true,
|
16
|
+
timeout_seconds: 3.0,
|
17
|
+
open_timeout_seconds: 1.0,
|
18
|
+
env: ENV["RAILS_ENV"] || "development",
|
19
|
+
enabled: false
|
20
|
+
}.freeze
|
21
|
+
|
22
|
+
class << self
|
23
|
+
# Load configuration from YAML file and environment variables
|
24
|
+
# @param rails_root [Pathname] Rails root path
|
25
|
+
# @return [OpenStruct] Configuration object
|
26
|
+
def load!(rails_root: Rails.root)
|
27
|
+
file = rails_root.join("config/langsmith.yml")
|
28
|
+
yml = File.exist?(file) ? YAML.load_file(file) : {}
|
29
|
+
env = (ENV["RAILS_ENV"] || "development").to_s
|
30
|
+
@config = OpenStruct.new(DEFAULTS.merge(yml.fetch(env, {})))
|
31
|
+
|
32
|
+
# Override with environment variables if present
|
33
|
+
@config.api_key = ENV["LANGSMITH_API_KEY"] if ENV["LANGSMITH_API_KEY"]
|
34
|
+
@config.project = ENV["LANGSMITH_PROJECT"] if ENV["LANGSMITH_PROJECT"]
|
35
|
+
@config.enabled = @config.api_key.present? unless ENV.key?("LANGSMITH_ENABLED")
|
36
|
+
@config.enabled = ENV["LANGSMITH_ENABLED"] == "true" if ENV.key?("LANGSMITH_ENABLED")
|
37
|
+
|
38
|
+
@config
|
39
|
+
end
|
40
|
+
|
41
|
+
# Access configuration values
|
42
|
+
# @param key [Symbol] Configuration key
|
43
|
+
# @return [Object] Configuration value
|
44
|
+
def [](key)
|
45
|
+
@config&.send(key)
|
46
|
+
end
|
47
|
+
|
48
|
+
# Set configuration values
|
49
|
+
# @param key [Symbol] Configuration key
|
50
|
+
# @param value [Object] Configuration value
|
51
|
+
# @return [Object] Configuration value
|
52
|
+
def set(key, value)
|
53
|
+
@config&.send("#{key}=", value)
|
54
|
+
end
|
55
|
+
|
56
|
+
# Get current configuration
|
57
|
+
# @return [OpenStruct] Configuration object
|
58
|
+
def current
|
59
|
+
@config ||= OpenStruct.new(DEFAULTS)
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
# For backwards compatibility
|
64
|
+
attr_accessor :enabled, :api_key, :project_name
|
65
|
+
|
66
|
+
def initialize
|
67
|
+
@enabled = false
|
68
|
+
@api_key = nil
|
69
|
+
@project_name = nil
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
@@ -0,0 +1,61 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "rails/generators"
|
4
|
+
|
5
|
+
module LangsmithrbRails
|
6
|
+
module Generators
|
7
|
+
# Generator for adding LangSmith support to a Rails application
|
8
|
+
class LangsmithGenerator < Rails::Generators::Base
|
9
|
+
source_root File.expand_path("templates", __dir__)
|
10
|
+
desc "Adds LangSmith support to your Rails application"
|
11
|
+
|
12
|
+
def create_initializer
|
13
|
+
template "langsmith_initializer.rb", "config/initializers/langsmith.rb"
|
14
|
+
end
|
15
|
+
|
16
|
+
def update_env_example
|
17
|
+
create_file ".env.example" unless File.exist?(".env.example")
|
18
|
+
|
19
|
+
# Check if LangSmith config is already in the file
|
20
|
+
env_content = File.exist?(".env.example") ? File.read(".env.example") : ""
|
21
|
+
return if env_content.include?("LANGSMITH_API_KEY")
|
22
|
+
|
23
|
+
append_to_file ".env.example" do
|
24
|
+
# Add a newline if the file doesn't end with one
|
25
|
+
(env_content.end_with?("\n") ? "" : "\n") +
|
26
|
+
<<~ENV
|
27
|
+
# LangSmith configuration
|
28
|
+
LANGSMITH_API_KEY=
|
29
|
+
LANGSMITH_PROJECT=
|
30
|
+
ENV
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
def update_gitignore
|
35
|
+
create_file ".gitignore" unless File.exist?(".gitignore")
|
36
|
+
|
37
|
+
# Check if .env is already in gitignore
|
38
|
+
gitignore_content = File.exist?(".gitignore") ? File.read(".gitignore") : ""
|
39
|
+
return if gitignore_content.match?(/^\.env\s*$/)
|
40
|
+
|
41
|
+
append_to_file ".gitignore" do
|
42
|
+
# Add a newline if the file doesn't end with one
|
43
|
+
(gitignore_content.end_with?("\n") ? "" : "\n") +
|
44
|
+
<<~GITIGNORE
|
45
|
+
# LangSmith
|
46
|
+
.env
|
47
|
+
GITIGNORE
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
def display_post_install_message
|
52
|
+
say "\n🎉 LangSmith support has been added to your Rails application!", :green
|
53
|
+
say "\nTo enable LangSmith tracing, add the following to your .env file:", :yellow
|
54
|
+
say "LANGSMITH_API_KEY=your_api_key", :yellow
|
55
|
+
say "LANGSMITH_PROJECT=your_project_name (optional)", :yellow
|
56
|
+
say "\nYou can get your API key from https://smith.langchain.com/", :yellow
|
57
|
+
say "\nRestart your Rails server to apply the changes.", :yellow
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
61
|
+
end
|
@@ -0,0 +1,22 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# Configure LangSmith using the langsmithrb gem
|
4
|
+
|
5
|
+
# First, configure the langsmithrb gem directly
|
6
|
+
Langsmithrb.configure do |config|
|
7
|
+
config.api_key = ENV["LANGSMITH_API_KEY"]
|
8
|
+
config.project_name = ENV["LANGSMITH_PROJECT"]
|
9
|
+
config.tracing_enabled = ENV["LANGSMITH_API_KEY"].present?
|
10
|
+
end
|
11
|
+
|
12
|
+
# Then, configure our Rails integration
|
13
|
+
LangsmithrbRails.configure do |config|
|
14
|
+
# Enable LangSmith tracing
|
15
|
+
config.enabled = ENV["LANGSMITH_API_KEY"].present?
|
16
|
+
|
17
|
+
# Your LangSmith API key from https://smith.langchain.com/
|
18
|
+
config.api_key = ENV["LANGSMITH_API_KEY"]
|
19
|
+
|
20
|
+
# Optional: The project name to use for LangSmith traces
|
21
|
+
config.project_name = ENV["LANGSMITH_PROJECT"]
|
22
|
+
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "langsmithrb"
|
4
|
+
|
5
|
+
module LangsmithrbRails
|
6
|
+
# LangSmith integration for Rails applications using the langsmithrb gem
|
7
|
+
module LangSmith
|
8
|
+
class << self
|
9
|
+
# Configure LangSmith tracing
|
10
|
+
# This method sets up LangSmith tracing using the langsmithrb gem
|
11
|
+
# @param api_key [String] LangSmith API key
|
12
|
+
# @param project_name [String] Optional project name for LangSmith traces
|
13
|
+
# @param tracing [Boolean] Whether to enable tracing (default: true)
|
14
|
+
def configure(api_key:, project_name: nil, tracing: true)
|
15
|
+
Langsmithrb.configure do |config|
|
16
|
+
config.api_key = api_key
|
17
|
+
config.project_name = project_name if project_name
|
18
|
+
config.tracing_enabled = tracing
|
19
|
+
end
|
20
|
+
end
|
21
|
+
|
22
|
+
# Check if LangSmith tracing is enabled
|
23
|
+
# @return [Boolean] Whether LangSmith tracing is enabled
|
24
|
+
def enabled?
|
25
|
+
Langsmithrb.config.tracing_enabled && !Langsmithrb.config.api_key.nil?
|
26
|
+
end
|
27
|
+
|
28
|
+
# Get the current LangSmith project name
|
29
|
+
# @return [String, nil] The current LangSmith project name or nil if not set
|
30
|
+
def project_name
|
31
|
+
Langsmithrb.config.project_name
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
@@ -0,0 +1,33 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "langsmithrb"
|
4
|
+
|
5
|
+
module LangsmithrbRails
|
6
|
+
# Rails integration for LangsmithrbRails
|
7
|
+
class Railtie < Rails::Railtie
|
8
|
+
initializer "langsmithrb_rails" do
|
9
|
+
# Configure LangSmith if enabled
|
10
|
+
if LangsmithrbRails.config.enabled && LangsmithrbRails.config.api_key
|
11
|
+
# Configure the langsmithrb gem
|
12
|
+
Langsmithrb.configure do |config|
|
13
|
+
config.api_key = LangsmithrbRails.config.api_key
|
14
|
+
config.project_name = LangsmithrbRails.config.project_name
|
15
|
+
config.tracing_enabled = true
|
16
|
+
end
|
17
|
+
|
18
|
+
# Also configure our wrapper for consistency
|
19
|
+
LangsmithrbRails::LangSmith.configure(
|
20
|
+
api_key: LangsmithrbRails.config.api_key,
|
21
|
+
project_name: LangsmithrbRails.config.project_name,
|
22
|
+
tracing: true
|
23
|
+
)
|
24
|
+
|
25
|
+
Rails.logger.info "LangSmith tracing enabled"
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
generators do
|
30
|
+
require_relative "generators/langsmithrb_rails/langsmith_generator"
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
@@ -0,0 +1,76 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
module LangsmithrbRails
|
4
|
+
# PII redaction utility for LangSmith traces
|
5
|
+
class Redactor
|
6
|
+
# Common PII patterns
|
7
|
+
PATTERNS = {
|
8
|
+
email: /\b[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Z|a-z]{2,}\b/,
|
9
|
+
phone: /\b(\+\d{1,2}\s?)?\(?\d{3}\)?[\s.-]?\d{3}[\s.-]?\d{4}\b/,
|
10
|
+
credit_card: /\b(?:\d{4}[-\s]?){3}\d{4}\b|\b\d{13,16}\b/,
|
11
|
+
ssn: /\b\d{3}[-\s]?\d{2}[-\s]?\d{4}\b/,
|
12
|
+
ip_address: /\b\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}\b/
|
13
|
+
}.freeze
|
14
|
+
|
15
|
+
class << self
|
16
|
+
# Allowlist of patterns that should not be redacted
|
17
|
+
attr_accessor :allowlist
|
18
|
+
|
19
|
+
# Custom patterns to redact beyond the defaults
|
20
|
+
attr_accessor :custom_patterns
|
21
|
+
|
22
|
+
# Initialize the class variables
|
23
|
+
def setup
|
24
|
+
@allowlist = []
|
25
|
+
@custom_patterns = {}
|
26
|
+
end
|
27
|
+
|
28
|
+
# Scrub PII from the input
|
29
|
+
# @param input [Object] Input to scrub (String, Hash, Array, etc.)
|
30
|
+
# @return [Object] Redacted copy of the input
|
31
|
+
def scrub(input)
|
32
|
+
return input unless Config[:redact_by_default]
|
33
|
+
|
34
|
+
case input
|
35
|
+
when String
|
36
|
+
scrub_string(input)
|
37
|
+
when Hash
|
38
|
+
input.transform_values { |v| scrub(v) }
|
39
|
+
when Array
|
40
|
+
input.map { |item| scrub(item) }
|
41
|
+
else
|
42
|
+
input
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
private
|
47
|
+
|
48
|
+
# Scrub PII from a string
|
49
|
+
# @param text [String] String to scrub
|
50
|
+
# @return [String] Redacted string
|
51
|
+
def scrub_string(text)
|
52
|
+
return text unless text.is_a?(String)
|
53
|
+
|
54
|
+
result = text.dup
|
55
|
+
|
56
|
+
# Skip redaction for allowlisted patterns
|
57
|
+
return result if @allowlist&.any? { |pattern| text.match?(pattern) }
|
58
|
+
|
59
|
+
# Apply default patterns
|
60
|
+
PATTERNS.each do |type, pattern|
|
61
|
+
result.gsub!(pattern) { |match| "[REDACTED #{type.upcase}]" }
|
62
|
+
end
|
63
|
+
|
64
|
+
# Apply custom patterns
|
65
|
+
@custom_patterns&.each do |type, pattern|
|
66
|
+
result.gsub!(pattern) { |match| "[REDACTED #{type.upcase}]" }
|
67
|
+
end
|
68
|
+
|
69
|
+
result
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
73
|
+
end
|
74
|
+
|
75
|
+
# Initialize class variables
|
76
|
+
LangsmithrbRails::Redactor.setup
|
@@ -0,0 +1,31 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require "langsmithrb"
|
4
|
+
require "rails"
|
5
|
+
|
6
|
+
require_relative "langsmithrb_rails/version"
|
7
|
+
require_relative "langsmithrb_rails/config"
|
8
|
+
require_relative "langsmithrb_rails/client"
|
9
|
+
require_relative "langsmithrb_rails/redactor"
|
10
|
+
require_relative "langsmithrb_rails/langsmith"
|
11
|
+
require_relative "langsmithrb_rails/railtie" if defined?(Rails)
|
12
|
+
|
13
|
+
# LangsmithRails provides integration with LangSmith for Rails applications
|
14
|
+
module LangsmithrbRails
|
15
|
+
class << self
|
16
|
+
# Configure LangsmithrbRails
|
17
|
+
# @yield [config] Configuration block
|
18
|
+
# @yieldparam config [LangsmithrbRails::Config] Configuration object
|
19
|
+
# @return [LangsmithrbRails::Config] Configuration object
|
20
|
+
def configure
|
21
|
+
yield config if block_given?
|
22
|
+
config
|
23
|
+
end
|
24
|
+
|
25
|
+
# Get the current configuration
|
26
|
+
# @return [LangsmithrbRails::Config] Configuration object
|
27
|
+
def config
|
28
|
+
@config ||= Config.new
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: langsmithrb_rails
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Protocol Grid
|
@@ -156,14 +156,67 @@ email:
|
|
156
156
|
executables: []
|
157
157
|
extensions: []
|
158
158
|
extra_rdoc_files: []
|
159
|
-
files:
|
160
|
-
|
159
|
+
files:
|
160
|
+
- ".rspec"
|
161
|
+
- ".rspec_status"
|
162
|
+
- CHANGELOG.md
|
163
|
+
- Gemfile
|
164
|
+
- Gemfile.lock
|
165
|
+
- LICENSE
|
166
|
+
- README.md
|
167
|
+
- Rakefile
|
168
|
+
- langsmithrb_rails-0.1.0.gem
|
169
|
+
- langsmithrb_rails.gemspec
|
170
|
+
- lib/generators/langsmithrb_rails/buffer/buffer_generator.rb
|
171
|
+
- lib/generators/langsmithrb_rails/buffer/templates/create_langsmith_run_buffers.rb
|
172
|
+
- lib/generators/langsmithrb_rails/buffer/templates/flush_buffer_job.rb
|
173
|
+
- lib/generators/langsmithrb_rails/buffer/templates/langsmith.rake
|
174
|
+
- lib/generators/langsmithrb_rails/buffer/templates/langsmith_run_buffer.rb
|
175
|
+
- lib/generators/langsmithrb_rails/buffer/templates/migration.rb
|
176
|
+
- lib/generators/langsmithrb_rails/ci/ci_generator.rb
|
177
|
+
- lib/generators/langsmithrb_rails/ci/templates/langsmith-evals.yml
|
178
|
+
- lib/generators/langsmithrb_rails/ci/templates/langsmith_export_summary.rb
|
179
|
+
- lib/generators/langsmithrb_rails/demo/demo_generator.rb
|
180
|
+
- lib/generators/langsmithrb_rails/demo/templates/chat_controller.js
|
181
|
+
- lib/generators/langsmithrb_rails/demo/templates/chat_controller.rb
|
182
|
+
- lib/generators/langsmithrb_rails/demo/templates/chat_message.rb
|
183
|
+
- lib/generators/langsmithrb_rails/demo/templates/create_chat_messages.rb
|
184
|
+
- lib/generators/langsmithrb_rails/demo/templates/index.html.erb
|
185
|
+
- lib/generators/langsmithrb_rails/demo/templates/llm_service.rb
|
186
|
+
- lib/generators/langsmithrb_rails/evals/evals_generator.rb
|
187
|
+
- lib/generators/langsmithrb_rails/evals/templates/checks/correctness.rb
|
188
|
+
- lib/generators/langsmithrb_rails/evals/templates/checks/llm_graded.rb
|
189
|
+
- lib/generators/langsmithrb_rails/evals/templates/datasets/sample.yml
|
190
|
+
- lib/generators/langsmithrb_rails/evals/templates/langsmith_evals.rake
|
191
|
+
- lib/generators/langsmithrb_rails/evals/templates/targets/http.rb
|
192
|
+
- lib/generators/langsmithrb_rails/evals/templates/targets/ruby.rb
|
193
|
+
- lib/generators/langsmithrb_rails/install/install_generator.rb
|
194
|
+
- lib/generators/langsmithrb_rails/install/templates/config.yml
|
195
|
+
- lib/generators/langsmithrb_rails/install/templates/initializer.rb
|
196
|
+
- lib/generators/langsmithrb_rails/privacy/privacy_generator.rb
|
197
|
+
- lib/generators/langsmithrb_rails/privacy/templates/custom_redactor.rb
|
198
|
+
- lib/generators/langsmithrb_rails/privacy/templates/privacy.yml
|
199
|
+
- lib/generators/langsmithrb_rails/privacy/templates/privacy_initializer.rb
|
200
|
+
- lib/generators/langsmithrb_rails/tracing/templates/langsmith_traced.rb
|
201
|
+
- lib/generators/langsmithrb_rails/tracing/templates/langsmith_traced_job.rb
|
202
|
+
- lib/generators/langsmithrb_rails/tracing/templates/request_tracing.rb
|
203
|
+
- lib/generators/langsmithrb_rails/tracing/tracing_generator.rb
|
204
|
+
- lib/langsmithrb_rails.rb
|
205
|
+
- lib/langsmithrb_rails/client.rb
|
206
|
+
- lib/langsmithrb_rails/config.rb
|
207
|
+
- lib/langsmithrb_rails/generators/langsmithrb_rails/langsmith_generator.rb
|
208
|
+
- lib/langsmithrb_rails/generators/langsmithrb_rails/templates/langsmith_initializer.rb
|
209
|
+
- lib/langsmithrb_rails/langsmith.rb
|
210
|
+
- lib/langsmithrb_rails/railtie.rb
|
211
|
+
- lib/langsmithrb_rails/redactor.rb
|
212
|
+
- lib/langsmithrb_rails/version.rb
|
213
|
+
homepage: https://github.com/cdaviis/langsmithrb_rails
|
161
214
|
licenses:
|
162
215
|
- MIT
|
163
216
|
metadata:
|
164
|
-
homepage_uri: https://github.com/
|
165
|
-
source_code_uri: https://github.com/
|
166
|
-
changelog_uri: https://github.com/
|
217
|
+
homepage_uri: https://github.com/cdaviis/langsmithrb_rails
|
218
|
+
source_code_uri: https://github.com/cdaviis/langsmithrb_rails
|
219
|
+
changelog_uri: https://github.com/cdaviis/langsmithrb_rails/blob/main/CHANGELOG.md
|
167
220
|
rdoc_options: []
|
168
221
|
require_paths:
|
169
222
|
- lib
|