Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
121 commits
Select commit Hold shift + click to select a range
2478c00
import tele changes first cut
zsimjee Dec 23, 2023
c479867
lint
zsimjee Jan 2, 2024
36e7570
correct telemetry lint
zsimjee Jan 3, 2024
9291d7b
sort out deps + lint
zsimjee Jan 3, 2024
09566f5
get throught test compilation
zsimjee Jan 3, 2024
cb9acd3
fix tests
zsimjee Jan 3, 2024
a23c963
bump version and add hub init
CalebCourier Jan 5, 2024
9a73eae
otel collector docker + trace exporter setup
zsimjee Jan 8, 2024
3ce50bb
remove metric exporter from ex
zsimjee Jan 8, 2024
573cdf2
lint + cosolidate standard tracer
zsimjee Jan 8, 2024
240663c
support hub:// syntax for RAIL xml
CalebCourier Jan 8, 2024
f85d3f6
magic string -> const, throw/warn on missing validator
CalebCourier Jan 8, 2024
33da859
start with simple refactor
CalebCourier Jan 9, 2024
2f8d513
stub out hub sub command
CalebCourier Jan 9, 2024
df07d0b
stub configure command, add logger
CalebCourier Jan 9, 2024
41487df
write to rc file
CalebCourier Jan 9, 2024
4022975
move install script to cli, add TODO's
CalebCourier Jan 9, 2024
b3e7ae1
review comments pt 1
zsimjee Jan 10, 2024
3e138e3
break up schema
zsimjee Jan 10, 2024
07ee4b1
refactor to isolate code for future move to server
CalebCourier Jan 10, 2024
f1996e6
Merge branch 'main' into hub-cli
CalebCourier Jan 11, 2024
b43bb61
install validators in namespace dir, install deps in site
CalebCourier Jan 12, 2024
9b03863
start tests
CalebCourier Jan 15, 2024
2189eb7
tests, lint, type
CalebCourier Jan 16, 2024
a873919
add unique id to rc file
CalebCourier Jan 16, 2024
2ced014
fix http import
CalebCourier Jan 17, 2024
a33c978
use validate-hub-service
CalebCourier Jan 18, 2024
8f1f726
stub out tests
CalebCourier Jan 18, 2024
05f5509
update cli with url, user id, and fail safe creds
CalebCourier Jan 24, 2024
e84f7a7
update cli doc
CalebCourier Jan 25, 2024
92d262f
Merge branch 'main' into otel
zsimjee Jan 31, 2024
614b23d
use env-var-based exports
zsimjee Feb 1, 2024
7bbb487
init preview for chaining
CalebCourier Feb 1, 2024
b2846fd
add validate and call
CalebCourier Feb 1, 2024
1613634
fix fix_reask, update test call to use integrate
CalebCourier Feb 1, 2024
2583903
fix ReadingTime
CalebCourier Feb 1, 2024
a14b1d3
add units
CalebCourier Feb 1, 2024
952b384
WIP
zsimjee Feb 2, 2024
5e5010f
fix reading time
CalebCourier Feb 5, 2024
dcfad5d
WIP server
zsimjee Feb 5, 2024
ec9e3c3
lint fixes
CalebCourier Feb 5, 2024
68b5877
refactor error class
CalebCourier Feb 5, 2024
2c0508c
update imports
CalebCourier Feb 5, 2024
f1c123b
first draft of lcel support
CalebCourier Feb 5, 2024
28952cd
type "fixes"
CalebCourier Feb 5, 2024
846dc14
fix string templating after split uri
zsimjee Feb 6, 2024
e9565ef
polyfills for 3.8
CalebCourier Feb 6, 2024
3c8f216
add link to tokens page
CalebCourier Feb 6, 2024
3e1f446
make missing rc file a warning instead of an error
CalebCourier Feb 6, 2024
56e3882
remove compile, add help for hub
zsimjee Feb 7, 2024
bb1fc04
validate creds after configure, success or error message
CalebCourier Feb 7, 2024
59c8836
Merge branch 'cli-bug-bash' of https://github.com/guardrails-ai/guard…
CalebCourier Feb 7, 2024
bb8ed35
lint fix
CalebCourier Feb 7, 2024
3eb335f
fix tests
CalebCourier Feb 7, 2024
a6403e0
Merge pull request #568 from guardrails-ai/lcel-support
zsimjee Feb 7, 2024
de905ef
lint, refactor high ordered client methods
CalebCourier Feb 7, 2024
9e40c44
fix tests
CalebCourier Feb 7, 2024
85a5c4d
server
zsimjee Feb 8, 2024
84341f0
start cli upload support
CalebCourier Feb 8, 2024
c35ad11
make original guard chainable
CalebCourier Feb 8, 2024
70a21ac
make guard and validator runnable
CalebCourier Feb 8, 2024
46da075
get rid of async-tester
zsimjee Feb 9, 2024
367ed99
Merge pull request #573 from guardrails-ai/runnable-validators
zsimjee Feb 12, 2024
276d20b
Merge pull request #571 from guardrails-ai/cli-bug-bash
zsimjee Feb 12, 2024
9b1b180
fix test
CalebCourier Feb 12, 2024
f16bb5c
impl create, start submit
CalebCourier Feb 12, 2024
69addbe
== to is
CalebCourier Feb 12, 2024
dd787e4
Merge branch 'hub-cli' into cli-upload
CalebCourier Feb 12, 2024
2516fa6
finish create add submit
CalebCourier Feb 13, 2024
9542f8c
Merge pull request #578 from guardrails-ai/cli-upload
zsimjee Feb 13, 2024
d408080
Merge pull request #537 from guardrails-ai/hub-cli
CalebCourier Feb 13, 2024
164dc1e
Merge branch 'hub-support' into chaining
CalebCourier Feb 13, 2024
eac1d89
Merge pull request #563 from guardrails-ai/chaining
CalebCourier Feb 13, 2024
79d799b
update post-install, lint
CalebCourier Feb 13, 2024
462d829
Validator Hub Telemetry (#559)
thekaranacharya Feb 13, 2024
cb013ae
update valdiator card format in docstring
CalebCourier Feb 14, 2024
20ccb67
Merge remote-tracking branch 'origin/hub-support' into otel
zsimjee Feb 14, 2024
816ed97
configure updates
CalebCourier Feb 14, 2024
c078f71
last area to share tracer
zsimjee Feb 14, 2024
02e6b24
update install success log to reference docs
CalebCourier Feb 14, 2024
2b6f612
create validator disclaimer
CalebCourier Feb 14, 2024
f2f1668
Merge branch 'hub-support' into otel
zsimjee Feb 14, 2024
763e76c
Merge pull request #525 from guardrails-ai/otel
zsimjee Feb 14, 2024
b7c68cd
submit description, update quick submit template
CalebCourier Feb 14, 2024
0676a4d
Merge branch 'hub-support' of https://github.com/guardrails-ai/guardr…
CalebCourier Feb 14, 2024
5314de6
Delete demo-test.py
zsimjee Feb 14, 2024
dca6554
Merge remote-tracking branch 'origin/main' into hub-support
zsimjee Feb 14, 2024
577965f
lint
zsimjee Feb 14, 2024
d258c41
50% pyrighted
zsimjee Feb 14, 2024
5d15907
make otel a req dep for context
zsimjee Feb 14, 2024
4ace01c
Lint
thekaranacharya Feb 14, 2024
ae355f8
FIx lint
thekaranacharya Feb 14, 2024
c155adb
guard type fixes
CalebCourier Feb 14, 2024
8425fe8
Merge branch 'hub-support' of https://github.com/guardrails-ai/guardr…
CalebCourier Feb 14, 2024
f63f4d9
typing fixes
CalebCourier Feb 14, 2024
4819801
more pyright
zsimjee Feb 14, 2024
442945d
clean pyright
zsimjee Feb 14, 2024
119a3db
lint
zsimjee Feb 14, 2024
a3ed32a
fix streaming tests
CalebCourier Feb 14, 2024
764855b
Merge branch 'hub-support' of https://github.com/guardrails-ai/guardr…
CalebCourier Feb 14, 2024
608ab1d
lint fix
CalebCourier Feb 14, 2024
47e6fd8
fix install test
zsimjee Feb 14, 2024
e877648
fix trace status
CalebCourier Feb 14, 2024
3ef37b8
sync cli dirs
CalebCourier Feb 14, 2024
32b9601
fix circular deps
CalebCourier Feb 14, 2024
75b10e8
lint fix
CalebCourier Feb 14, 2024
bf3d542
fix cli refs that py 3.8 doesn't understand
CalebCourier Feb 14, 2024
91b1882
lint fix
CalebCourier Feb 15, 2024
b7205f6
another lint
CalebCourier Feb 15, 2024
b989432
ignore type get_annotations
CalebCourier Feb 15, 2024
895040e
type ignore polyfill
CalebCourier Feb 15, 2024
1c090b7
lint
CalebCourier Feb 15, 2024
08cbe1f
use classmethod to default encoder
CalebCourier Feb 15, 2024
4af9f78
update action plugins, remove cache
CalebCourier Feb 15, 2024
47b69c5
skip test for pydantic 1
CalebCourier Feb 15, 2024
78e7c59
lint
CalebCourier Feb 15, 2024
96a2e38
try to assign name to mock, doesn't fail locally
CalebCourier Feb 15, 2024
5454fcc
try mocking utils
CalebCourier Feb 15, 2024
4a0fac3
litn
CalebCourier Feb 15, 2024
63111e1
get rid of broken mock
CalebCourier Feb 15, 2024
9c78b59
fix async version of test
CalebCourier Feb 15, 2024
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
57 changes: 28 additions & 29 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,6 @@ on:
branches:
- main
- dev
- "0.3.0"

# Allows you to run this workflow manually from the Actions tab
workflow_dispatch:
Expand All @@ -21,17 +20,17 @@ jobs:
matrix:
python-version: ["3.8", "3.9", "3.10", "3.11"]
steps:
- uses: actions/checkout@v2
- uses: actions/checkout@v4
- name: Set up Python ${{ matrix.python-version }}
uses: actions/setup-python@v2
uses: actions/setup-python@v5
with:
python-version: ${{ matrix.python-version }}

- name: Poetry cache
uses: actions/cache@v3
with:
path: ~/.cache/pypoetry
key: poetry-cache-${{ runner.os }}-${{ matrix.python-version }}-${{ env.POETRY_VERSION }}
# - name: Poetry cache
# uses: actions/cache@v3
# with:
# path: ~/.cache/pypoetry
# key: poetry-cache-${{ runner.os }}-${{ matrix.python-version }}-${{ env.POETRY_VERSION }}

- name: Install Poetry
uses: snok/install-poetry@v1
Expand All @@ -53,17 +52,17 @@ jobs:
pydantic-version: ["1.10.9", "2.4.2"]
openai-version: ["0.28.1", "1.2.4"]
steps:
- uses: actions/checkout@v2
- uses: actions/checkout@v4
- name: Set up Python ${{ matrix.python-version }}
uses: actions/setup-python@v2
uses: actions/setup-python@v5
with:
python-version: ${{ matrix.python-version }}

- name: Poetry cache
uses: actions/cache@v3
with:
path: ~/.cache/pypoetry
key: poetry-cache-${{ runner.os }}-${{ matrix.python-version }}-${{ env.POETRY_VERSION }}-${{ matrix.pydantic-version }}
# - name: Poetry cache
# uses: actions/cache@v3
# with:
# path: ~/.cache/pypoetry
# key: poetry-cache-${{ runner.os }}-${{ matrix.python-version }}-${{ env.POETRY_VERSION }}-${{ matrix.pydantic-version }}

- name: Install Poetry
uses: snok/install-poetry@v1
Expand Down Expand Up @@ -106,17 +105,17 @@ jobs:
pydantic-version: ["1.10.9", "2.4.2"]
openai-version: ["0.28.1", "1.2.4"]
steps:
- uses: actions/checkout@v2
- uses: actions/checkout@v4
- name: Set up Python ${{ matrix.python-version }}
uses: actions/setup-python@v2
uses: actions/setup-python@v5
with:
python-version: ${{ matrix.python-version }}

- name: Poetry cache
uses: actions/cache@v3
with:
path: ~/.cache/pypoetry
key: poetry-cache-${{ runner.os }}-${{ matrix.python-version }}-${{ env.POETRY_VERSION }}-${{ matrix.pydantic-version }}-${{ matrix.openai-version }}
# - name: Poetry cache
# uses: actions/cache@v3
# with:
# path: ~/.cache/pypoetry
# key: poetry-cache-${{ runner.os }}-${{ matrix.python-version }}-${{ env.POETRY_VERSION }}-${{ matrix.pydantic-version }}-${{ matrix.openai-version }}

- name: Install Poetry
uses: snok/install-poetry@v1
Expand Down Expand Up @@ -154,16 +153,16 @@ jobs:
NLTK_DATA: /tmp/nltk_data
steps:
- name: Checkout repository
uses: actions/checkout@v2
uses: actions/checkout@v4
- name: Set up Python
uses: actions/setup-python@v4
uses: actions/setup-python@v5
with:
python-version: 3.11.x
- name: Poetry cache
uses: actions/cache@v3
with:
path: ~/.cache/pypoetry
key: poetry-cache-${{ runner.os }}-3.11.x-${{ env.POETRY_VERSION }}
# - name: Poetry cache
# uses: actions/cache@v3
# with:
# path: ~/.cache/pypoetry
# key: poetry-cache-${{ runner.os }}-3.11.x-${{ env.POETRY_VERSION }}
- name: Install Poetry
uses: snok/install-poetry@v1
with:
Expand Down
2 changes: 1 addition & 1 deletion docs/api_reference/response_structures.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,4 +6,4 @@
- "ValidationResult"
- "PassResult"
- "FailResult"
- "ValidatorError"
- "ValidationError"
15 changes: 14 additions & 1 deletion docs/cli.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,4 +7,17 @@ Guardrails can be used from the command line to validate the output of an LLM. C

```bash
guardrails validate <path to rail spec> <llm output as string> --out <output path for validated JSON>
```
```

## Validator Hub
In addition to providing a command line interface for validation, the guardrails cli also supports interacting with the Validator Hub.

### Configuration
In order to access any Validators from the Hub that require authentication, you will need to set up your environment through the `guardrails configure` command. Before running `guardrails configure`, go to the [Validator Hub]() to generate your access tokens. [Add more detail on this process].

Once you have your tokens, run `guardrails configure` and enter the client id and client secret you retrieved above.

Also, if you want to opt out of anonymous metrics collection, you can do this now by specifying `--no-metrics=true`.

### Installing Validators
In order to install a validator from the hub, you can find its identifier on its respective page in the [Validator Hub](). This identifier is shaped as a namespace and a name: `{namespace}/{validator_name}`. Once you have this you can go to any project where you have guardrails installed and run `guardrails hub install hub://{namespace}/{validator_name}`.
10 changes: 5 additions & 5 deletions docs/examples/input_validation.ipynb
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@
"source": [
"When `fix` is specified as the on-fail handler, the prompt will automatically be amended before calling the LLM.\n",
"\n",
"In any other case (for example, `exception`), a `ValidatorError` will be returned in the outcome."
"In any other case (for example, `exception`), a `ValidationError` will be returned in the outcome."
]
},
{
Expand All @@ -67,13 +67,13 @@
],
"source": [
"import openai\n",
"from guardrails.errors import ValidatorError\n",
"from guardrails.errors import ValidationError\n",
"\n",
"try:\n",
" guard(\n",
" openai.chat.completions.create,\n",
" )\n",
"except ValidatorError as e:\n",
"except ValidationError as e:\n",
" print(e)"
]
},
Expand Down Expand Up @@ -115,7 +115,7 @@
" openai.chat.completions.create,\n",
" prompt=\"This is not two words\",\n",
" )\n",
"except ValidatorError as e:\n",
"except ValidationError as e:\n",
" print(e)"
]
}
Expand All @@ -136,7 +136,7 @@
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.11.6"
"version": "3.11.7"
}
},
"nbformat": 4,
Expand Down
10 changes: 5 additions & 5 deletions docs/examples/response_is_on_topic.ipynb
Original file line number Diff line number Diff line change
Expand Up @@ -137,7 +137,7 @@
"source": [
"import guardrails as gd\n",
"from guardrails.validators import OnTopic\n",
"from guardrails.errors import ValidatorError\n",
"from guardrails.errors import ValidationError\n",
"\n",
"# Create the Guard with the OnTopic Validator\n",
"guard = gd.Guard.from_string(\n",
Expand All @@ -159,7 +159,7 @@
" guard.parse(\n",
" llm_output=text,\n",
" )\n",
"except ValidatorError as e:\n",
"except ValidationError as e:\n",
" print(e)\n"
]
},
Expand Down Expand Up @@ -205,7 +205,7 @@
" guard.parse(\n",
" llm_output=text,\n",
" )\n",
"except ValidatorError as e:\n",
"except ValidationError as e:\n",
" print(e)"
]
},
Expand Down Expand Up @@ -258,7 +258,7 @@
" guard.parse(\n",
" llm_output=text,\n",
" )\n",
"except ValidatorError as e:\n",
"except ValidationError as e:\n",
" print(e)"
]
}
Expand All @@ -279,7 +279,7 @@
"name": "python",
"nbconvert_exporter": "python",
"pygments_lexer": "ipython3",
"version": "3.11.6"
"version": "3.11.7"
}
},
"nbformat": 4,
Expand Down
5 changes: 5 additions & 0 deletions docs/telemetry.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
1. Go to grafana
2. search for opentelemetry in data sources
3. Create a token, paste in the resulting file to otel-collector-config.yml
4. docker-compose up -f telemetry/docker-compose.yml up
5. run a guard and look for traces
4 changes: 3 additions & 1 deletion guardrails/classes/__init__.py
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
from guardrails.classes.credentials import Credentials
from guardrails.classes.input_type import InputType
from guardrails.classes.output_type import OT
from guardrails.classes.validation_outcome import ValidationOutcome

__all__ = ["ValidationOutcome", "OT"]
__all__ = ["ValidationOutcome", "OT", "InputType", "Credentials"]
31 changes: 31 additions & 0 deletions guardrails/classes/credentials.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
import os
from dataclasses import dataclass
from os.path import expanduser
from typing import Optional

from guardrails.classes.generic.serializeable import Serializeable


@dataclass
class Credentials(Serializeable):
id: Optional[str] = None
client_id: Optional[str] = None
client_secret: Optional[str] = None
no_metrics: Optional[bool] = False

@staticmethod
def from_rc_file() -> "Credentials":
try:
home = expanduser("~")
guardrails_rc = os.path.join(home, ".guardrailsrc")
with open(guardrails_rc) as rc_file:
lines = rc_file.readlines()
creds = {}
for line in lines:
key, value = line.split("=", 1)
creds[key.strip()] = value.strip()
rc_file.close()
return Credentials.from_dict(creds)

except FileNotFoundError:
return Credentials.from_dict({}) # type: ignore
3 changes: 2 additions & 1 deletion guardrails/classes/generic/__init__.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
from guardrails.classes.generic.serializeable import Serializeable
from guardrails.classes.generic.stack import Stack

__all__ = ["Stack"]
__all__ = ["Stack", "Serializeable"]
52 changes: 52 additions & 0 deletions guardrails/classes/generic/serializeable.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
import inspect
import json
import sys
from dataclasses import InitVar, asdict, dataclass, field, is_dataclass
from json import JSONEncoder
from typing import Any, Dict

from pydash.strings import snake_case


def get_annotations(obj):
if sys.version_info.minor >= 10 and hasattr(inspect, "get_annotations"):
return inspect.get_annotations(obj) # type: ignore
else:
return obj.__annotations__


class SerializeableJSONEncoder(JSONEncoder):
def default(self, o):
if is_dataclass(o):
return asdict(o)
return super().default(o)


encoder_kwargs = {}
if sys.version_info.minor >= 10:
encoder_kwargs["kw_only"] = True
encoder_kwargs["default"] = SerializeableJSONEncoder


@dataclass
class Serializeable:
encoder: InitVar[JSONEncoder] = field(**encoder_kwargs)

@classmethod
def from_dict(cls, data: Dict[str, Any]):
annotations = get_annotations(cls)
attributes = dict.keys(annotations)
snake_case_kwargs = {
snake_case(k): data.get(k) for k in data if snake_case(k) in attributes
}
snake_case_kwargs["encoder"] = snake_case_kwargs.get(
"encoder", SerializeableJSONEncoder
)
return cls(**snake_case_kwargs) # type: ignore

@property
def __dict__(self) -> Dict[str, Any]:
return asdict(self)

def to_json(self):
return json.dumps(self, cls=self.encoder) # type: ignore
4 changes: 2 additions & 2 deletions guardrails/classes/generic/stack.py
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ def search(self, x: T) -> Optional[int]:
except ValueError:
pass

def at(self, index: int) -> Optional[T]:
def at(self, index: int, default: Optional[T] = None) -> Optional[T]:
"""Returns the item located at the index.

If the index does not exist in the stack (Overflow or
Expand All @@ -59,7 +59,7 @@ def at(self, index: int) -> Optional[T]:
value = self[index]
return value
except IndexError:
pass
return default

def copy(self) -> "Stack[T]":
"""Returns a copy of the current Stack."""
Expand Down
11 changes: 8 additions & 3 deletions guardrails/classes/history/call.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@
sub_reasks_with_fixed_values,
)
from guardrails.utils.safe_get import get_value_from_path
from guardrails.validator_base import Refrain
from guardrails.validator_base import Filter, Refrain


# We can't inherit from Iteration because python
Expand Down Expand Up @@ -315,8 +315,13 @@ def _has_unresolved_failures(self) -> bool:
output = self.fixed_output
for failure in self.failed_validations:
value = get_value_from_path(output, failure.property_path)
if value == failure.value_before_validation or isinstance(
failure.value_after_validation, Refrain
if (
# NOTE: this means on_fail="fix" was applied
# to a Validator without a programmatic fix.
(value is None and failure.value_before_validation is not None)
or value == failure.value_before_validation
or isinstance(failure.value_after_validation, Refrain)
or isinstance(failure.value_after_validation, Filter)
):
return True

Expand Down
5 changes: 5 additions & 0 deletions guardrails/classes/input_type.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
from typing import TypeVar

from langchain_core.messages import BaseMessage

InputType = TypeVar("InputType", str, BaseMessage)
12 changes: 12 additions & 0 deletions guardrails/cli/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
import guardrails.cli.configure # noqa
import guardrails.cli.validate # noqa
from guardrails.cli.guardrails import guardrails as cli
from guardrails.cli.hub import hub_command

cli.add_typer(
hub_command, name="hub", help="Manage validators installed from the Guardrails Hub."
)


if __name__ == "__main__":
cli()
Loading