TLSN proof agent (#7)

* plugin prompts

* init : make separate agent for plugin.

* init plugin description agent

* prompt to check the tlsn proof that user will upload, need to work on the actual skill to accomplish that
This commit is contained in:
jayssj11
2024-09-17 18:46:18 +05:30
committed by GitHub
parent ddd9d5bb8c
commit f69f43550a
5 changed files with 341 additions and 0 deletions

View File

@@ -0,0 +1,86 @@
import autogen
import os
import json
from dotenv import load_dotenv
from typing import Annotated
import requests
from plugin_prompts import bank_plugin_prompts
load_dotenv() # take environment variables from .env.
config_list = [
{
'model': 'gpt-3.5-turbo',
'api_key': os.getenv('OPENAI_API_KEY'),
}
]
llm_config = {
"timeout": 120,
"seed": 42, # for caching. once task is run it caches the response,
"config_list": config_list,
"temperature": 0 #lower temperature more standard lesss creative response, higher is more creative
}
def write_plugin(website_url:Annotated[str, "website url"], plugin_name:Annotated[str, "plugin name"]) -> Annotated[dict, "The response from the plugin"] | None:
api_url = f"https://archive.prove.email/api/key?domain={domain}"
response = requests.get(api_url)
print("response : ", response)
return response.json() if response.status_code == 200 else None
plugin_agent = autogen.AssistantAgent(
name="plugin_agent",
llm_config=llm_config,
system_message="""you will write TLSN plugin for the website that the user will provide.
You will ask the user to provide the website url,
API and some web request and response of it and plugin name.
Once you receive the url, use the write_plugin function to write the plugin.
The function will return the response from the plugin.
Analyze the response to gather the following information from the plugin: plugin name, plugin description, plugin author, plugin version, website url.
""",
)
user_proxy = autogen.UserProxyAgent(
name="user_proxy",
human_input_mode="ALWAYS",
max_consecutive_auto_reply=3,
is_termination_msg=lambda x: x.get("content", "").rstrip().endswith("TERMINATE"),
code_execution_config={
"last_n_messages": 3,
"work_dir": "code",
"use_docker": False,
},
llm_config=llm_config,
system_message="""Reply TERMINATE if the task has been solved at full satisfaction
otherwise, reply CONTINUE, or the reason why the task is not solved yet."""
)
user_proxy.register_for_llm(name="write_plugin", description="write TLSN extension plugin for website that user will provide")(write_plugin)
user_proxy.register_for_execution(name="write_plugin")(write_plugin)
def main():
# Register the verify_email_with_prove_api function for the email_assistant
plugin_agent.register_function(
function_map={
"write_plugin": write_plugin,
}
)
chat_results = user_proxy.initiate_chats([
{
"recipient": plugin_agent,
"message": "I want to write a TLSN extension plugin for the website that I will provide, please help me",
"silent": False,
"summary_method": "reflection_with_llm"
}
])
for i, chat_res in enumerate(chat_results):
print(f"*****{i}th chat*******:")
print(chat_res.summary)
print("Human input in the middle:", chat_res.human_input)
print("Conversation cost: ", chat_res.cost)
print("\n\n")
if __name__ == "__main__":
main()

View File

@@ -0,0 +1,233 @@
bank_plugin_prompts = """
your task is to build tlsn browser extension plugins for the website. I can give you sample code below, that you can refer
to make such plugins. I will give you a task description and you have to build the plugin to do the task.
You will ask users to give the website url, API link / route, auth method.
Here is the task description:
Ask users to provide the website url, API link. Make sure to ask user if TLSN extension is installed. If not, ask them to install it.
Ask users to provide the auth method. Make sure to ask user if TLSN extension is installed. If not, ask them to install it.
Ask users to provide the API link. Make sure to ask user if TLSN extension is installed. If not, ask them to install it.
Here is the sample code below for twitter profile notarization example
import icon from '../assets/icon.png';
import config_json from '../config.json';
import { redirect, notarize, outputJSON, getCookiesByHost, getHeadersByHost } from './utils/hf.js';
/**
* Plugin configuration
* This configurations defines the plugin, most importantly:
* * the different steps
* * the user data (headers, cookies) it will access
* * the web requests it will query (or notarize)
*/
export function config() {
outputJSON({
...config_json,
icon: icon
});
}
function isValidHost(urlString: string) {
const url = new URL(urlString);
return url.hostname === 'twitter.com' || url.hostname === 'x.com';
}
/**
* Implementation of the first (start) plugin step
*/
export function start() {
if (!isValidHost(Config.get('tabUrl'))) {
redirect('https://x.com');
outputJSON(false);
return;
}
outputJSON(true);
}
/**
* Implementation of step "two".
* This step collects and validates authentication cookies and headers for 'api.x.com'.
* If all required information, it creates the request object.
* Note that the url needs to be specified in the `config` too, otherwise the request will be refused.
*/
export function two() {
const cookies = getCookiesByHost('api.x.com');
const headers = getHeadersByHost('api.x.com');
if (
!cookies.auth_token ||
!cookies.ct0 ||
!headers['x-csrf-token'] ||
!headers['authorization']
) {
outputJSON(false);
return;
}
outputJSON({
url: 'https://api.x.com/1.1/account/settings.json',
method: 'GET',
headers: {
'x-twitter-client-language': 'en',
'x-csrf-token': headers['x-csrf-token'],
Host: 'api.x.com',
authorization: headers.authorization,
Cookie: `lang=en; auth_token=${cookies.auth_token}; ct0=${cookies.ct0}`,
'Accept-Encoding': 'identity',
Connection: 'close',
},
secretHeaders: [
`x-csrf-token: ${headers['x-csrf-token']}`,
`cookie: lang=en; auth_token=${cookies.auth_token}; ct0=${cookies.ct0}`,
`authorization: ${headers.authorization}`,
],
});
}
/**
* This method is used to parse the Twitter response and specify what information is revealed (i.e. **not** redacted)
* This method is optional in the notarization request. When it is not specified nothing is redacted.
*
* In this example it locates the `screen_name` and excludes that range from the revealed response.
*/
export function parseTwitterResp() {
const bodyString = Host.inputString();
const params = JSON.parse(bodyString);
if (params.screen_name) {
const revealed = `"screen_name":"${params.screen_name}"`;
const selectionStart = bodyString.indexOf(revealed);
const selectionEnd =
selectionStart + revealed.length;
const secretResps = [
bodyString.substring(0, selectionStart),
bodyString.substring(selectionEnd, bodyString.length),
];
outputJSON(secretResps);
} else {
outputJSON(false);
}
}
/**
* Step 3: calls the `notarize` host function
*/
export function three() {
const params = JSON.parse(Host.inputString());
if (!params) {
outputJSON(false);
} else {
const id = notarize({
...params,
getSecretResponse: 'parseTwitterResp',
});
outputJSON(id);
}
}
Below is the sample config.json that above code uses:
{
"title": "Twitter Profile",
"description": "Notarize ownership of a twitter profile",
"steps": [
{
"title": "Visit Twitter website",
"cta": "Go to x.com",
"action": "start"
},
{
"title": "Collect credentials",
"description": "Login to your account if you haven't already",
"cta": "Check cookies",
"action": "two"
},
{
"title": "Notarize twitter profile",
"cta": "Notarize",
"action": "three",
"prover": true
}
],
"hostFunctions": [
"redirect",
"notarize"
],
"cookies": [
"api.x.com"
],
"headers": [
"api.x.com"
],
"requests": [
{
"url": "https://api.x.com/1.1/account/settings.json",
"method": "GET"
}
]
}
You need to make the config json for user's use case. You can use the sample config.json as a reference.
below is the hf.js file that above code uses:
function redirect(url) {
const { redirect } = Host.getFunctions();
const mem = Memory.fromString(url);
redirect(mem.offset);
}
function notarize(options) {
const { notarize } = Host.getFunctions();
const mem = Memory.fromString(JSON.stringify(options));
const idOffset = notarize(mem.offset);
const id = Memory.find(idOffset).readString();
return id;
}
function outputJSON(json) {
Host.outputString(
JSON.stringify(json),
);
}
function getCookiesByHost(hostname) {
const cookies = JSON.parse(Config.get('cookies'));
if (!cookies[hostname]) throw new Error(`cannot find cookies for ${hostname}`);
return cookies[hostname];
}
function getHeadersByHost(hostname) {
const headers = JSON.parse(Config.get('headers'));
if (!headers[hostname]) throw new Error(`cannot find headers for ${hostname}`);
return headers[hostname];
}
module.exports = {
redirect,
notarize,
outputJSON,
getCookiesByHost,
getHeadersByHost,
};
You have to build the plugin to do the task. You can use the sample code as a reference.
You have to use the following format to build the plugin:
Plugin Name: {plugin_name} // name will be asked by user
Plugin Description: {plugin_description}
Plugin Code: // you will generate plugin code based on the sample code above
{plugin_code}
Remember to use the sample code as a reference and not copy and paste it directly.
Your response should be in the following format:
Plugin Name: {plugin_name}
Plugin Description: {plugin_description}
Plugin Code:
{plugin_code}
"""

View File

@@ -13,14 +13,22 @@ cffi==1.16.0
chardet==5.2.0
charset-normalizer==3.3.2
click==8.1.7
colorama==0.4.6
cryptography==42.0.8
dataclasses-json==0.6.7
deepdiff==7.0.1
diskcache==5.6.3
distro==1.9.0
dkimpy==1.1.8
dnspython==2.6.1
docker==7.1.0
emoji==2.12.1
filetype==1.2.0
FLAML==2.1.2
frozenlist==1.4.1
gitdb==4.0.11
GitPython==3.1.43
greenlet==3.0.3
h11==0.14.0
httpcore==1.0.5
httpx==0.27.0
@@ -48,6 +56,7 @@ nest-asyncio==1.6.0
nltk==3.8.1
numpy==1.26.4
ollama==0.2.1
openai==1.35.7
opencv-contrib-python==4.10.0.84
opencv-python==4.10.0.84
ordered-set==4.1.0
@@ -63,6 +72,7 @@ pillow==10.3.0
pillow_heif==0.16.0
protobuf==4.25.3
pyarrow==16.1.0
pyautogen==0.2.31
pycparser==2.22
pycryptodome==3.20.0
pydantic==2.7.4
@@ -77,6 +87,7 @@ python-dotenv==1.0.1
python-iso639==2024.4.27
python-magic==0.4.27
pytz==2024.1
pywin32==306
PyYAML==6.0.1
rapidfuzz==3.9.3
referencing==0.35.1
@@ -94,6 +105,8 @@ SQLAlchemy==2.0.30
streamlit==1.35.0
tabulate==0.9.0
tenacity==8.3.0
termcolor==2.4.0
tiktoken==0.7.0
toml==0.10.2
tomli==2.0.1
toolz==0.12.1
@@ -106,5 +119,6 @@ tzdata==2024.1
unstructured==0.14.6
unstructured-client==0.23.3
urllib3==2.2.1
watchdog==4.0.1
wrapt==1.16.0
yarl==1.9.4

View File

@@ -21,4 +21,12 @@ account number, bank balance.
Ensure the details match with the bank.json file.
Add additional keys to the bank.json file and save it.
If there are any errors in processing the PDF, inform the user and ask for a different PDF.
"""
verify_tlsn_proof_prompt = """
Ask user to paste the tlsn proof in the terminal and you will save that proof in a file called tlsn_proof.json. it will be a json file.
Remember the json contents and you will use verify_tlsn_proof skill to upload the proof to explorer.tlsn.org. Once we get the confirmation
that the proof is valid and it contains the correct details that user have provided we can proceed to give out loans. The information we are
looking for are name and country. If possible account number too but name and country is enough of a proof.
Once we get the proof we can give out loans.
"""

0
verify_tlsn_proof.py Normal file
View File