This commit is contained in:
Luk
2026-03-16 14:55:27 +08:00
commit 7a191d4e2a
21 changed files with 1027 additions and 0 deletions

113
.gitignore vendored Executable file
View File

@@ -0,0 +1,113 @@
# See https://help.github.com/articles/ignoring-files/ for more about ignoring files.
# how to include another gitignore?
# https://stackoverflow.com/questions/7005142/can-i-include-other-gitignore-file-in-a-gitignore-file-like-include-in-c-li
# https://github.com/github/gitignore
# https://github.com/SlideWave/gitignore-include?tab=readme-ov-file#examples
# https://gitignore.io
### .gitignore.global.txt ###
# Self defined pattern to ignore
?*.gitignore
?*.gitignore/
?*.gitignore.*
?*.gitignore.*/
*.gitomit
*.gitomit.*
*.gitomit/
*.gitomit.*/
*.nogit
*.nogit.*
*.nogit/
*.nogit.*/
# 保留
!.gitignore
!.gitignore.*
!.gitkeep
# 通用
.svn/
.deploy_git/
.idea/
.sass-cache/
.wrangler
/test/unit/coverage/
/test/e2e/reports/
node_modules/
*.aab
*.apk
*.ipa
*.min.js
*.min.css
*.min.html
*.iml
*.njsproj
*.ntvs*
*.sw*
*.sln
*.suo
.gitattributes
.umi
.umi-production
npm-debug.log*
yarn-debug.log*
yarn-error.log*
yarn.lock
selenium-debug.log
Thumbs.db
thumbs.db
_desktop.ini
# vue-cli 项目
/dist/
# 来自 vue-cli 创建项目的 .gitignore
.project
# hexo
/public/
# Hardhat
/artifacts/
/cache/
# seafile 临时文件
._*
.$*
# office 暂存文件
~$*
# 用户shell配置脚本
.bashrc_custom
# 苹果系统临时文件
.DS_Store
# 安卓缓存文件夹
.thumbnails
# local env files
.env.local
.env.*.local
# hexo
/db.json
# wo
# 服务端
/_archive/*
/_datastore/*
/_filestore/*
/_logstore/*
/_webroot/*
/_ssl/*
# uniapp 客户端
/unpackage/*
!/unpackage/res/
package-lock.json
pages4loader.json5
### .gitignore.local.txt ###

1
.python-version Normal file
View File

@@ -0,0 +1 @@
3.10

44
1-generation.mjs Normal file
View File

@@ -0,0 +1,44 @@
import OpenAI from 'openai'
import * as z from 'zod'
const client = new OpenAI({
apiKey:
'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'
}) // or set environment: export OPENAI_API_KEY=...
// const CalendarEvent = {
// type: 'object',
// properties: {
// name: { type: 'string' },
// date: { type: 'string' },
// participants: { type: 'array' }
// },
// additionalProperties: false,
// required: ['name', 'date', 'participants']
// }
const response = await client.responses.create({
model: 'gpt-5-nano',
reasoning: { effort: 'low' },
// instructions: 'Talk like a pirate',
input: [
{ role: 'system', content: 'extract the event information' },
{
role: 'user',
content:
'Write a nodejs script to create a calendar event with the following information: name: "Birthday Party", date: "2024-07-20", participants: ["Alice", "Bob"]'
}
]
// text: {
// format: {
// type: 'json_schema',
// strict: true,
// schema: CalendarEvent,
// name: 'event'
// }
// }
})
console.log(JSON.stringify(response.output, null, 2)) // response.output_text/output_parsed
// 从 gpt-5.4 起,推荐使用通用模型来生成代码。

82
2-tc-function.mjs Normal file
View File

@@ -0,0 +1,82 @@
import OpenAI from 'openai'
const openai = new OpenAI({
apiKey:
'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'
}) // or set environment: export OPENAI_API_KEY=...
const my = {
model: 'gpt-5-nano'
}
const tools = [
{
type: 'function',
name: 'get_horoscope',
description: "Get today's horoscope for an astrological sign.",
parameters: {
type: 'object',
properties: {
sign: {
type: 'string',
description: 'An astrological sign like Taurus or Aquarius'
}
},
required: ['sign']
}
}
]
const api = {
get_horoscope ({ sign } = {}) {
return sign + ' Next Tuesday you will befriend a baby otter.'
}
}
// Create a running input list we will add to over time
let input = [
{ role: 'user', content: 'What is my horoscope? I am an Aquarius.' }
]
// 2. Prompt the model with tools defined
let response = await openai.responses.create({
model: my.model,
tools,
input
})
console.log('==========Response 1. round')
console.log(JSON.stringify(response, null, 2)) // response.output_text/output_parsed
input.push(...response.output) // add the model's response to the input, including any function calls, otherwise the next request reports: 'BadRequestError: 400 No tool call found for function call output with call_id ...'
response.output.forEach(item => {
if (item.type == 'function_call') {
if (typeof api[item.name] === 'function') {
console.log('function call =', item)
const function_call_output = api[item.name](JSON.parse(item.arguments))
console.log('function call output =', function_call_output)
// 4. Provide function call results to the model
input.push({
type: 'function_call_output',
call_id: item.call_id,
output: function_call_output.toString()
})
}
}
})
console.log('=========Input appended with function call output')
console.log(JSON.stringify(input, null, 2))
response = await openai.responses.create({
model: my.model,
//instructions: 'Respond only with a horoscope generated by a tool.',
tools,
input
})
// 5. The model should be able to give a response!
console.log('============Final output:')
console.log(JSON.stringify(response.output, null, 2))

31
3-tc-websearch.mjs Normal file
View File

@@ -0,0 +1,31 @@
import OpenAI from 'openai'
const openai = new OpenAI({
apiKey:
'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'
}) // or set environment: export OPENAI_API_KEY=...
const my = {
model: 'gpt-5-nano'
}
const tools = [
{
type: 'web_search'
}
]
let input = [
{
role: 'user',
content: 'Tell me the most up-to-date news about the war in Iran'
}
]
let response = await openai.responses.create({
model: my.model,
tools,
input
})
console.log('==========Response')
console.log(JSON.stringify(response, null, 2)) // response.output_text/output_parsed

81
4-tc-shell.mjs Normal file
View File

@@ -0,0 +1,81 @@
import OpenAI from 'openai'
import shell from 'shelljs'
import { execSync } from 'node:child_process'
const openai = new OpenAI({
apiKey:
'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'
}) // or set environment: export OPENAI_API_KEY=...
const my = {
model: 'gpt-5.2' // hosted shell is not available in gpt-5 or gpt-5-nano/mini, so using gpt-5.2 for this example
}
console.log('==========Hosted shell environment============')
let responseHosted = await openai.responses.create({
model: my.model,
tools: [
{
type: 'shell',
environment: {
type: 'container_auto',
network_policy: {
type: 'allowlist',
allowed_domains: ['npmjs.org', 'tic.cc']
} // hosted shell has no network access by default, but you can allowlist domains as needed. The allowlist must literally be a subset of organizational allowlist configured on the web.
}
}
],
input: [
{
role: 'user',
content:
// 'In the shell, Run `node -v` at first, then npm init a project, then install the package express, and finally run npm list to show the installed version.'
'Run `node -v` and disable http.sslVerify for git. Then npm init a project ./hosted_project, then install the package git+https://git.tic.cc/open/wo_scripts, and finally run npm list to show the installed version.'
}
]
})
console.log('========== responseHosted.output =')
console.log(JSON.stringify(responseHosted.output, null, 2)) // response.output/output_text/output_parsed
//////////////////////////////////////////
console.log('==========local shell environment============')
let responseLocal = await openai.responses.create({
model: my.model,
tools: [
{
type: 'shell',
environment: { type: 'local' }
}
],
input: [
{
role: 'user',
content:
'Run npm init a project at ./local_project, then install the package git+https://git.tic.cc/open/wo_scripts, and finally run npm list to show the installed version.'
}
]
})
console.log('========== responseLocal.output =')
console.log(JSON.stringify(responseLocal.output, null, 2)) // response.output/output_text/output_parsed
responseLocal.output.forEach(item => {
if (item.type == 'shell_call') {
console.log('shell call item =', item)
item.action.commands.forEach(command => {
console.log('$', command, '\n')
let shell_call_command_output = shell.exec(command, {
silent: true
}).stdout
console.log(shell_call_command_output)
})
// 4. Provide shell command results to the model
// In this example we just log it, but in a real implementation you would likely want to send the output back to the model in another request so it can learn from the results of its commands and decide what to do next.
}
})

100
5-tc-browser.mjs Normal file
View File

@@ -0,0 +1,100 @@
import OpenAI from 'openai'
import { chromium } from 'playwright'
const openai = new OpenAI({
apiKey:
'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'
}) // or set environment: export OPENAI_API_KEY=...
const my = {
model: 'gpt-5.4' // computer tool is only available in gpt-5.4 or later
}
const browser = await chromium.launch({
headless: false,
chromiumSandbox: true,
env: {},
args: ['--disable-extensions', '--disable-file-system']
})
const page = await browser.newPage({
viewport: { width: 1280, height: 720 },
url: 'https://www.bing.com'
})
async function handleComputerActions (page, actions) {
for (const action of actions) {
switch (action.type) {
case 'click':
await page.mouse.click(action.x, action.y, {
button: action.button ?? 'left'
})
break
case 'double_click':
await page.mouse.dblclick(action.x, action.y, {
button: action.button ?? 'left'
})
break
case 'scroll':
await page.mouse.move(action.x, action.y)
await page.mouse.wheel(action.scrollX ?? 0, action.scrollY ?? 0)
break
case 'keypress':
for (const key of action.keys) {
await page.keyboard.press(key === 'SPACE' ? ' ' : key)
}
break
case 'type':
await page.keyboard.type(action.text)
break
case 'wait':
case 'screenshot':
break
default:
throw new Error(`Unsupported action: ${action.type}`)
}
}
}
async function computerUseLoop (target, response) {
while (true) {
const computerCall = response.output.find(
item => item.type === 'computer_call'
)
if (!computerCall) {
return response
}
await handleComputerActions(target, computerCall.actions)
const screenshot = await page.screenshot({ type: 'png' })
const screenshotBase64 = Buffer.from(screenshot).toString('base64')
response = await openai.responses.create({
model: my.model,
tools: [{ type: 'computer' }],
previous_response_id: response.id,
input: [
{
type: 'computer_call_output',
call_id: computerCall.call_id,
output: {
type: 'computer_screenshot',
image_url: `data:image/png;base64,${screenshotBase64}`,
detail: 'original'
}
}
]
})
}
}
const response = await openai.responses.create({
model: my.model,
tools: [{ type: 'computer' }],
input:
"visit agidin.com and tell me what's the title of the page, then screenshot the page and save it as homepage.png"
})
console.log(JSON.stringify(response.output, null, 2))
computerUseLoop(page, response)

251
6-tc-computer.ts Normal file
View File

@@ -0,0 +1,251 @@
// Run with:
// bun run 6-tc-computer.ts
// Override the user prompt with:
// bun run 6-tc-computer.ts --prompt "Go to example.com and summarize the page."
// Note: this script intentionally leaves the Playwright browser open after the
// model reaches a final answer. Because the browser/context are not closed,
// Bun stays alive until you close the browser or stop the process manually.
// model reaches a final answer. Because the browser/context are not closed,
// Bun stays alive until you close the browser or stop the process manually.
import OpenAI from 'openai'
import readline from 'node:readline/promises'
import vm from 'node:vm'
import { chromium } from 'playwright'
import util from 'node:util'
import shell from 'shelljs'
const sleep = ms => new Promise((resolve, reject) => setTimeout(resolve, ms))
async function main (
prompt: string = 'Show a welcome message on screen. After the task is complete, ask the user to confirm before ending the program, or ask user for more tasks to perform on the website.',
max_steps: number = 10,
model: string = 'gpt-5.2'
) {
const client = new OpenAI({
apiKey:
'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'
})
const rl = readline.createInterface({
input: process.stdin,
output: process.stdout
})
const browser = await chromium.launch({
headless: false,
args: ['--window-size=1440,900']
})
const context = await browser.newContext({
viewport: { width: 1440, height: 900 }
})
const page = await context.newPage()
const conversation: any[] = []
const js_output: any[] = []
const sandbox: Record<string, any> = {
console: {
log: (...xs: any[]) => {
js_output.push({
type: 'input_text',
text: util.formatWithOptions(
{ showHidden: false, getters: false, maxStringLength: 2000 },
...xs
)
})
}
},
browser: browser,
context: context,
page: page,
display: (base64_image: string) => {
// Remove whitespace/newlines from base64 which can invalidate OpenAI API
const cleanB64 = base64_image.replace(/\s+/g, '')
js_output.push({
type: 'input_image',
image_url: `data:image/png;base64,${cleanB64}`,
detail: 'original'
})
}
}
const ctx = vm.createContext(sandbox)
conversation.push({
role: 'user',
content: prompt
})
for (let i = 0; i < max_steps; i++) {
console.log(`\n=== ROUND ${i + 1} ===\n`)
//await sleep(1000) // pause between rounds for readability
const resp = await client.responses.create({
model,
tools: [
{
type: 'shell',
environment: { type: 'local' }
},
{
type: 'function' as const,
name: 'exec_js',
description:
'Execute provided interactive JavaScript in a persistent REPL context.',
parameters: {
type: 'object',
properties: {
code: {
type: 'string',
description: `
JavaScript to execute. Write small snippets of interactive code. To persist variables or functions across tool calls, you must save them to globalThis. Code is executed in an async node:vm context, so you can use await. You have access to ONLY the following:
- console.log(x): Use this to read contents back to you. But be minimal: otherwise the output may be too long. Avoid using console.log() for large base64 payloads like screenshots or buffer. If you create an image or screenshot, pass the base64 string to display().
- display(base64_image_string): Use this to view a base64-encoded image.
- Do not write screenshots or image data to temporary files or disk just to pass them back. Keep image data in memory and send it directly to display().
- Do not assume package globals like Bun.file are available unless they are explicitly provided.
- browser: A playwright chromium browser instance.
- context: A playwright browser context with viewport 1440x900.
- page: A playwright page already created in that context.
`
}
},
required: ['code'],
additionalProperties: false
}
},
{
type: 'function' as const,
name: 'ask_user',
description:
'Ask the user a clarification question and wait for their response.',
parameters: {
type: 'object',
properties: {
question: {
type: 'string',
description:
'The exact question to show the human. Use this instead of answering with a freeform clarifying question in a final answer.'
}
},
required: ['question'],
additionalProperties: false
}
},
{
type: 'function' as const,
name: 'end_program',
description:
'End the program and close the browser. Call this when the task is complete.',
parameters: {
type: 'object',
properties: {},
required: []
}
}
],
input: conversation,
reasoning: {
effort: 'low'
}
})
// Save model outputs into the running conversation
conversation.push(...resp.output)
// Handle tool calls
for (const item of resp.output) {
console.log('response output item =', item)
if (item.type == 'shell_call') {
console.log('shell call item =', item)
let shell_call_output = []
item.action.commands.forEach(command => {
console.log('$', command, '\n')
let { stdout, stderr } = shell.exec(command, {
silent: true
})
shell_call_output.push({
stdout,
stderr,
outcome: { type: 'exit', exit_code: 0 }
})
})
conversation.push({
type: 'shell_call_output',
call_id: item.call_id,
output: shell_call_output
})
} else if (item.type === 'function_call' && item.name === 'exec_js') {
const parsed = JSON.parse(item.arguments ?? '{}') as {
code?: string
}
const code = parsed.code ?? ''
console.log(code)
console.log('----')
const wrappedCode = `
(async () => {
${code}
})();
`
try {
await new vm.Script(wrappedCode, {
filename: 'exec_js.js'
}).runInContext(ctx)
} catch (e: any) {
sandbox.console.log(e, e?.message, e?.stack)
}
// Send tool output back to the model, keyed by call_id
conversation.push({
type: 'function_call_output',
call_id: item.call_id,
output: js_output.slice()
})
for (const out of js_output) {
if (out.type === 'input_text') {
console.log('JS LOG:', out.text)
} else if (out.type === 'input_image') {
console.log('JS IMAGE: [base64 string omitted]')
}
}
console.log('=====')
js_output.length = 0
} else if (item.type === 'function_call' && item.name === 'ask_user') {
const parsed = JSON.parse(item.arguments ?? '{}') as {
question?: string
}
const question = parsed.question ?? 'Please provide more information.'
console.log(`MODEL QUESTION: ${question}`)
const answer = await rl.question('> ')
conversation.push({
type: 'function_call_output',
call_id: item.call_id,
output: answer
})
} else if (item.type === 'function_call' && item.name === 'end_program') {
console.log('Closing browser and exiting program...')
await browser.close()
rl.close()
process.exit(0)
} else if (item.type === 'message') {
console.log('Message:', item.content[0]?.text ?? item.content)
}
} // end of for loop iterations for tool calls and outputs
} // end of main for loop for max_steps
}
function getCliPrompt (): string | undefined {
const args = Bun.argv.slice(2)
for (let i = 0; i < args.length; i++) {
if (args[i] === '--prompt') {
return args[i + 1]
}
}
return undefined
}
main(getCliPrompt()).catch(err => {
console.error('Error occurred:', err)
process.exit(1)
})

21
7-tc-code.mjs Normal file
View File

@@ -0,0 +1,21 @@
import OpenAI from 'openai'
const client = new OpenAI({
apiKey:
'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'
})
const resp = await client.responses.create({
model: 'gpt-5-nano',
tools: [
{
type: 'code_interpreter',
container: { type: 'auto', memory_limit: '4g' }
}
],
instructions:
"You are a python code interpreter running inside a container. When you execute code, you will get the output back. Use this to perform calculations or manipulate data as needed to answer the user's question.",
input: 'solve 3x+11=58'
// 'convert "Hello world" to CIDv0 and return the result'
})
console.log(JSON.stringify(resp.output, null, 2))

29
Dockerfile Normal file
View File

@@ -0,0 +1,29 @@
FROM ubuntu:22.04
ENV DEBIAN_FRONTEND=noninteractive
RUN apt-get update && apt-get install -y \
xfce4 \
xfce4-goodies \
xrdp \
xvfb \
xdotool \
imagemagick \
x11-apps \
sudo \
software-properties-common \
firefox-esr \
&& apt-get remove -y light-locker xfce4-screensaver xfce4-power-manager || true \
&& apt-get clean \
&& rm -rf /var/lib/apt/lists/*
RUN useradd -ms /bin/bash myuser && echo "myuser ALL=(ALL) NOPASSWD:ALL" >> /etc/sudoers
COPY entrypoint.sh /home/myuser/entrypoint.sh
RUN chmod +x /home/myuser/entrypoint.sh && chown myuser:myuser /home/myuser/entrypoint.sh
USER myuser
WORKDIR /home/myuser
EXPOSE 5900
CMD ["/home/myuser/entrypoint.sh"]

0
README.md Normal file
View File

BIN
babelyx.com.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.2 MiB

16
entrypoint.sh Normal file
View File

@@ -0,0 +1,16 @@
#!/bin/bash
# Create VNC password file if it doesn't exist
if [ ! -f /home/myuser/.vncpass ]; then
x11vnc -storepasswd secret /home/myuser/.vncpass
fi
# Start the services
Xvfb :99 -screen 0 1280x800x24 >/dev/null 2>&1 &
x11vnc -display :99 -forever -rfbauth /home/myuser/.vncpass -listen 0.0.0.0 -rfbport 5900 >/dev/null 2>&1 &
export DISPLAY=:99
startxfce4 >/dev/null 2>&1 &
sleep 2
echo 'Container running!'
tail -f /dev/null

6
hello.py Normal file
View File

@@ -0,0 +1,6 @@
def main():
print("Hello from aitest!")
if __name__ == "__main__":
main()

26
package.json Normal file
View File

@@ -0,0 +1,26 @@
{
"name": "try",
"version": "1.0.0",
"description": "",
"main": "apitest.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"author": "",
"license": "ISC",
"dependencies": {
"base-x": "^5.0.1",
"ipfs-only-hash": "^4.0.0",
"openai": "^6.25.0",
"playwright": "^1.58.2",
"shelljs": "^0.10.0",
"tic-crypto": "git+https://git.tic.cc/open/tic-crypto",
"wo_scripts": "git+https://git.tic.cc/open/wo_scripts",
"zod": "^4.3.6"
},
"devDependencies": {
"@types/bun": "^1.3.10",
"ts-node": "^10.9.2",
"typescript": "^5.9.3"
}
}

10
pyproject.toml Normal file
View File

@@ -0,0 +1,10 @@
[project]
name = "aitest"
version = "0.1.0"
description = "Add your description here"
readme = "README.md"
requires-python = ">=3.10"
dependencies = [
"base58>=2.1.1",
"requests>=2.32.5",
]

36
result.md Normal file
View File

@@ -0,0 +1,36 @@
```js
// create-event.js
// npm install ics
const { createEvent } = require(\"ics\");
const fs = require(\"fs\");
const event = {
title: \"Birthday Party\",
start: [2024, 7, 20], // YYYY, M, D
duration: { hours: 2 },
attendees: [
{ name: \"Alice\" },
{ name: \"Bob\" }
]
};
createEvent(event, (error, value) => {
if (error) {
console.error(\"Error creating event:\", error);
return;
}
fs.writeFileSync(\"birthday-party.ics\", value);
console.log(\"Calendar event created: birthday-party.ics\");
});
```
Run it with:
```bash
npm install ics
node create-event.js
```
This will generate a `birthday-party.ics` file you can import into a calendar app.

14
skills/contacts/skill.md Normal file
View File

@@ -0,0 +1,14 @@
---
name: contacts
description: My contact list
---
Use this skill when you need to find details of a contact of mine.
Here are my contacts:
```
name, phone
Xue Hua, 18617591633
Luk Lu, 15295439901
Zong Qiaozhen, 13585016982
```

3
skills/skill_cid.js Normal file
View File

@@ -0,0 +1,3 @@
const ipfsOnlyHash = require('ipfs-only-hash')
ipfsOnlyHash.of(content, option)

6
skills/skill_cid.md Normal file
View File

@@ -0,0 +1,6 @@
---
name: basic-math
description: Add or multiply numbers.
---
Use this skill when you need to calcuate cid of a string.

157
uv.lock generated Normal file
View File

@@ -0,0 +1,157 @@
version = 1
requires-python = ">=3.10"
[[package]]
name = "aitest"
version = "0.1.0"
source = { virtual = "." }
dependencies = [
{ name = "base58" },
{ name = "requests" },
]
[package.metadata]
requires-dist = [
{ name = "base58", specifier = ">=2.1.1" },
{ name = "requests", specifier = ">=2.32.5" },
]
[[package]]
name = "base58"
version = "2.1.1"
source = { registry = "https://pypi.org/simple" }
sdist = { url = "https://files.pythonhosted.org/packages/7f/45/8ae61209bb9015f516102fa559a2914178da1d5868428bd86a1b4421141d/base58-2.1.1.tar.gz", hash = "sha256:c5d0cb3f5b6e81e8e35da5754388ddcc6d0d14b6c6a132cb93d69ed580a7278c", size = 6528 }
wheels = [
{ url = "https://files.pythonhosted.org/packages/4a/45/ec96b29162a402fc4c1c5512d114d7b3787b9d1c2ec241d9568b4816ee23/base58-2.1.1-py3-none-any.whl", hash = "sha256:11a36f4d3ce51dfc1043f3218591ac4eb1ceb172919cebe05b52a5bcc8d245c2", size = 5621 },
]
[[package]]
name = "certifi"
version = "2026.2.25"
source = { registry = "https://pypi.org/simple" }
sdist = { url = "https://files.pythonhosted.org/packages/af/2d/7bf41579a8986e348fa033a31cdd0e4121114f6bce2457e8876010b092dd/certifi-2026.2.25.tar.gz", hash = "sha256:e887ab5cee78ea814d3472169153c2d12cd43b14bd03329a39a9c6e2e80bfba7", size = 155029 }
wheels = [
{ url = "https://files.pythonhosted.org/packages/9a/3c/c17fb3ca2d9c3acff52e30b309f538586f9f5b9c9cf454f3845fc9af4881/certifi-2026.2.25-py3-none-any.whl", hash = "sha256:027692e4402ad994f1c42e52a4997a9763c646b73e4096e4d5d6db8af1d6f0fa", size = 153684 },
]
[[package]]
name = "charset-normalizer"
version = "3.4.5"
source = { registry = "https://pypi.org/simple" }
sdist = { url = "https://files.pythonhosted.org/packages/1d/35/02daf95b9cd686320bb622eb148792655c9412dbb9b67abb5694e5910a24/charset_normalizer-3.4.5.tar.gz", hash = "sha256:95adae7b6c42a6c5b5b559b1a99149f090a57128155daeea91732c8d970d8644", size = 134804 }
wheels = [
{ url = "https://files.pythonhosted.org/packages/a7/21/a2b1505639008ba2e6ef03733a81fc6cfd6a07ea6139a2b76421230b8dad/charset_normalizer-3.4.5-cp310-cp310-macosx_10_9_universal2.whl", hash = "sha256:4167a621a9a1a986c73777dbc15d4b5eac8ac5c10393374109a343d4013ec765", size = 283319 },
{ url = "https://files.pythonhosted.org/packages/70/67/df234c29b68f4e1e095885c9db1cb4b69b8aba49cf94fac041db4aaf1267/charset_normalizer-3.4.5-cp310-cp310-manylinux2014_aarch64.manylinux_2_17_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:3f64c6bf8f32f9133b668c7f7a7cbdbc453412bc95ecdbd157f3b1e377a92990", size = 189974 },
{ url = "https://files.pythonhosted.org/packages/df/7f/fc66af802961c6be42e2c7b69c58f95cbd1f39b0e81b3365d8efe2a02a04/charset_normalizer-3.4.5-cp310-cp310-manylinux2014_ppc64le.manylinux_2_17_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:568e3c34b58422075a1b49575a6abc616d9751b4d61b23f712e12ebb78fe47b2", size = 207866 },
{ url = "https://files.pythonhosted.org/packages/c9/23/404eb36fac4e95b833c50e305bba9a241086d427bb2167a42eac7c4f7da4/charset_normalizer-3.4.5-cp310-cp310-manylinux2014_s390x.manylinux_2_17_s390x.manylinux_2_28_s390x.whl", hash = "sha256:036c079aa08a6a592b82487f97c60b439428320ed1b2ea0b3912e99d30c77765", size = 203239 },
{ url = "https://files.pythonhosted.org/packages/4b/2f/8a1d989bfadd120c90114ab33e0d2a0cbde05278c1fc15e83e62d570f50a/charset_normalizer-3.4.5-cp310-cp310-manylinux2014_x86_64.manylinux_2_17_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:340810d34ef83af92148e96e3e44cb2d3f910d2bf95e5618a5c467d9f102231d", size = 196529 },
{ url = "https://files.pythonhosted.org/packages/a5/0c/c75f85ff7ca1f051958bb518cd43922d86f576c03947a050fbedfdfb4f15/charset_normalizer-3.4.5-cp310-cp310-manylinux_2_31_armv7l.whl", hash = "sha256:cd2d0f0ec9aa977a27731a3209ebbcacebebaf41f902bd453a928bfd281cf7f8", size = 184152 },
{ url = "https://files.pythonhosted.org/packages/f9/20/4ed37f6199af5dde94d4aeaf577f3813a5ec6635834cda1d957013a09c76/charset_normalizer-3.4.5-cp310-cp310-manylinux_2_31_riscv64.manylinux_2_39_riscv64.whl", hash = "sha256:0b362bcd27819f9c07cbf23db4e0e8cd4b44c5ecd900c2ff907b2b92274a7412", size = 195226 },
{ url = "https://files.pythonhosted.org/packages/28/31/7ba1102178cba7c34dcc050f43d427172f389729e356038f0726253dd914/charset_normalizer-3.4.5-cp310-cp310-musllinux_1_2_aarch64.whl", hash = "sha256:77be992288f720306ab4108fe5c74797de327f3248368dfc7e1a916d6ed9e5a2", size = 192933 },
{ url = "https://files.pythonhosted.org/packages/4b/23/f86443ab3921e6a60b33b93f4a1161222231f6c69bc24fb18f3bee7b8518/charset_normalizer-3.4.5-cp310-cp310-musllinux_1_2_armv7l.whl", hash = "sha256:8b78d8a609a4b82c273257ee9d631ded7fac0d875bdcdccc109f3ee8328cfcb1", size = 185647 },
{ url = "https://files.pythonhosted.org/packages/82/44/08b8be891760f1f5a6d23ce11d6d50c92981603e6eb740b4f72eea9424e2/charset_normalizer-3.4.5-cp310-cp310-musllinux_1_2_ppc64le.whl", hash = "sha256:ba20bdf69bd127f66d0174d6f2a93e69045e0b4036dc1ca78e091bcc765830c4", size = 209533 },
{ url = "https://files.pythonhosted.org/packages/3b/5f/df114f23406199f8af711ddccfbf409ffbc5b7cdc18fa19644997ff0c9bb/charset_normalizer-3.4.5-cp310-cp310-musllinux_1_2_riscv64.whl", hash = "sha256:76a9d0de4d0eab387822e7b35d8f89367dd237c72e82ab42b9f7bf5e15ada00f", size = 195901 },
{ url = "https://files.pythonhosted.org/packages/07/83/71ef34a76fe8aa05ff8f840244bda2d61e043c2ef6f30d200450b9f6a1be/charset_normalizer-3.4.5-cp310-cp310-musllinux_1_2_s390x.whl", hash = "sha256:8fff79bf5978c693c9b1a4d71e4a94fddfb5fe744eb062a318e15f4a2f63a550", size = 204950 },
{ url = "https://files.pythonhosted.org/packages/58/40/0253be623995365137d7dc68e45245036207ab2227251e69a3d93ce43183/charset_normalizer-3.4.5-cp310-cp310-musllinux_1_2_x86_64.whl", hash = "sha256:c7e84e0c0005e3bdc1a9211cd4e62c78ba80bc37b2365ef4410cd2007a9047f2", size = 198546 },
{ url = "https://files.pythonhosted.org/packages/ed/5c/5f3cb5b259a130895ef5ae16b38eaf141430fa3f7af50cd06c5d67e4f7b2/charset_normalizer-3.4.5-cp310-cp310-win32.whl", hash = "sha256:58ad8270cfa5d4bef1bc85bd387217e14ff154d6630e976c6f56f9a040757475", size = 132516 },
{ url = "https://files.pythonhosted.org/packages/a5/c3/84fb174e7770f2df2e1a2115090771bfbc2227fb39a765c6d00568d1aab4/charset_normalizer-3.4.5-cp310-cp310-win_amd64.whl", hash = "sha256:02a9d1b01c1e12c27883b0c9349e0bcd9ae92e727ff1a277207e1a262b1cbf05", size = 142906 },
{ url = "https://files.pythonhosted.org/packages/d7/b2/6f852f8b969f2cbd0d4092d2e60139ab1af95af9bb651337cae89ec0f684/charset_normalizer-3.4.5-cp310-cp310-win_arm64.whl", hash = "sha256:039215608ac7b358c4da0191d10fc76868567fbf276d54c14721bdedeb6de064", size = 133258 },
{ url = "https://files.pythonhosted.org/packages/8f/9e/bcec3b22c64ecec47d39bf5167c2613efd41898c019dccd4183f6aa5d6a7/charset_normalizer-3.4.5-cp311-cp311-macosx_10_9_universal2.whl", hash = "sha256:610f72c0ee565dfb8ae1241b666119582fdbfe7c0975c175be719f940e110694", size = 279531 },
{ url = "https://files.pythonhosted.org/packages/58/12/81fd25f7e7078ab5d1eedbb0fac44be4904ae3370a3bf4533c8f2d159acd/charset_normalizer-3.4.5-cp311-cp311-manylinux2014_aarch64.manylinux_2_17_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:60d68e820af339df4ae8358c7a2e7596badeb61e544438e489035f9fbf3246a5", size = 188006 },
{ url = "https://files.pythonhosted.org/packages/ae/6e/f2d30e8c27c1b0736a6520311982cf5286cfc7f6cac77d7bc1325e3a23f2/charset_normalizer-3.4.5-cp311-cp311-manylinux2014_ppc64le.manylinux_2_17_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:10b473fc8dca1c3ad8559985794815f06ca3fc71942c969129070f2c3cdf7281", size = 205085 },
{ url = "https://files.pythonhosted.org/packages/d0/90/d12cefcb53b5931e2cf792a33718d7126efb116a320eaa0742c7059a95e4/charset_normalizer-3.4.5-cp311-cp311-manylinux2014_s390x.manylinux_2_17_s390x.manylinux_2_28_s390x.whl", hash = "sha256:d4eb8ac7469b2a5d64b5b8c04f84d8bf3ad340f4514b98523805cbf46e3b3923", size = 200545 },
{ url = "https://files.pythonhosted.org/packages/03/f4/44d3b830a20e89ff82a3134912d9a1cf6084d64f3b95dcad40f74449a654/charset_normalizer-3.4.5-cp311-cp311-manylinux2014_x86_64.manylinux_2_17_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:5bcb3227c3d9aaf73eaaab1db7ccd80a8995c509ee9941e2aae060ca6e4e5d81", size = 193863 },
{ url = "https://files.pythonhosted.org/packages/25/4b/f212119c18a6320a9d4a730d1b4057875cdeabf21b3614f76549042ef8a8/charset_normalizer-3.4.5-cp311-cp311-manylinux_2_31_armv7l.whl", hash = "sha256:75ee9c1cce2911581a70a3c0919d8bccf5b1cbc9b0e5171400ec736b4b569497", size = 181827 },
{ url = "https://files.pythonhosted.org/packages/74/00/b26158e48b425a202a92965f8069e8a63d9af1481dfa206825d7f74d2a3c/charset_normalizer-3.4.5-cp311-cp311-manylinux_2_31_riscv64.manylinux_2_39_riscv64.whl", hash = "sha256:1d1401945cb77787dbd3af2446ff2d75912327c4c3a1526ab7955ecf8600687c", size = 191085 },
{ url = "https://files.pythonhosted.org/packages/c4/c2/1c1737bf6fd40335fe53d28fe49afd99ee4143cc57a845e99635ce0b9b6d/charset_normalizer-3.4.5-cp311-cp311-musllinux_1_2_aarch64.whl", hash = "sha256:0a45e504f5e1be0bd385935a8e1507c442349ca36f511a47057a71c9d1d6ea9e", size = 190688 },
{ url = "https://files.pythonhosted.org/packages/5a/3d/abb5c22dc2ef493cd56522f811246a63c5427c08f3e3e50ab663de27fcf4/charset_normalizer-3.4.5-cp311-cp311-musllinux_1_2_armv7l.whl", hash = "sha256:e09f671a54ce70b79a1fc1dc6da3072b7ef7251fadb894ed92d9aa8218465a5f", size = 183077 },
{ url = "https://files.pythonhosted.org/packages/44/33/5298ad4d419a58e25b3508e87f2758d1442ff00c2471f8e0403dab8edad5/charset_normalizer-3.4.5-cp311-cp311-musllinux_1_2_ppc64le.whl", hash = "sha256:d01de5e768328646e6a3fa9e562706f8f6641708c115c62588aef2b941a4f88e", size = 206706 },
{ url = "https://files.pythonhosted.org/packages/7b/17/51e7895ac0f87c3b91d276a449ef09f5532a7529818f59646d7a55089432/charset_normalizer-3.4.5-cp311-cp311-musllinux_1_2_riscv64.whl", hash = "sha256:131716d6786ad5e3dc542f5cc6f397ba3339dc0fb87f87ac30e550e8987756af", size = 191665 },
{ url = "https://files.pythonhosted.org/packages/90/8f/cce9adf1883e98906dbae380d769b4852bb0fa0004bc7d7a2243418d3ea8/charset_normalizer-3.4.5-cp311-cp311-musllinux_1_2_s390x.whl", hash = "sha256:1a374cc0b88aa710e8865dc1bd6edb3743c59f27830f0293ab101e4cf3ce9f85", size = 201950 },
{ url = "https://files.pythonhosted.org/packages/08/ca/bce99cd5c397a52919e2769d126723f27a4c037130374c051c00470bcd38/charset_normalizer-3.4.5-cp311-cp311-musllinux_1_2_x86_64.whl", hash = "sha256:d31f0d1671e1534e395f9eb84a68e0fb670e1edb1fe819a9d7f564ae3bc4e53f", size = 195830 },
{ url = "https://files.pythonhosted.org/packages/87/4f/2e3d023a06911f1281f97b8f036edc9872167036ca6f55cc874a0be6c12c/charset_normalizer-3.4.5-cp311-cp311-win32.whl", hash = "sha256:cace89841c0599d736d3d74a27bc5821288bb47c5441923277afc6059d7fbcb4", size = 132029 },
{ url = "https://files.pythonhosted.org/packages/fe/1f/a853b73d386521fd44b7f67ded6b17b7b2367067d9106a5c4b44f9a34274/charset_normalizer-3.4.5-cp311-cp311-win_amd64.whl", hash = "sha256:f8102ae93c0bc863b1d41ea0f4499c20a83229f52ed870850892df555187154a", size = 142404 },
{ url = "https://files.pythonhosted.org/packages/b4/10/dba36f76b71c38e9d391abe0fd8a5b818790e053c431adecfc98c35cd2a9/charset_normalizer-3.4.5-cp311-cp311-win_arm64.whl", hash = "sha256:ed98364e1c262cf5f9363c3eca8c2df37024f52a8fa1180a3610014f26eac51c", size = 132796 },
{ url = "https://files.pythonhosted.org/packages/9c/b6/9ee9c1a608916ca5feae81a344dffbaa53b26b90be58cc2159e3332d44ec/charset_normalizer-3.4.5-cp312-cp312-macosx_10_13_universal2.whl", hash = "sha256:ed97c282ee4f994ef814042423a529df9497e3c666dca19be1d4cd1129dc7ade", size = 280976 },
{ url = "https://files.pythonhosted.org/packages/f8/d8/a54f7c0b96f1df3563e9190f04daf981e365a9b397eedfdfb5dbef7e5c6c/charset_normalizer-3.4.5-cp312-cp312-manylinux2014_aarch64.manylinux_2_17_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:0294916d6ccf2d069727d65973c3a1ca477d68708db25fd758dd28b0827cff54", size = 189356 },
{ url = "https://files.pythonhosted.org/packages/42/69/2bf7f76ce1446759a5787cb87d38f6a61eb47dbbdf035cfebf6347292a65/charset_normalizer-3.4.5-cp312-cp312-manylinux2014_ppc64le.manylinux_2_17_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:dc57a0baa3eeedd99fafaef7511b5a6ef4581494e8168ee086031744e2679467", size = 206369 },
{ url = "https://files.pythonhosted.org/packages/10/9c/949d1a46dab56b959d9a87272482195f1840b515a3380e39986989a893ae/charset_normalizer-3.4.5-cp312-cp312-manylinux2014_s390x.manylinux_2_17_s390x.manylinux_2_28_s390x.whl", hash = "sha256:ed1a9a204f317ef879b32f9af507d47e49cd5e7f8e8d5d96358c98373314fc60", size = 203285 },
{ url = "https://files.pythonhosted.org/packages/67/5c/ae30362a88b4da237d71ea214a8c7eb915db3eec941adda511729ac25fa2/charset_normalizer-3.4.5-cp312-cp312-manylinux2014_x86_64.manylinux_2_17_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:7ad83b8f9379176c841f8865884f3514d905bcd2a9a3b210eaa446e7d2223e4d", size = 196274 },
{ url = "https://files.pythonhosted.org/packages/b2/07/c9f2cb0e46cb6d64fdcc4f95953747b843bb2181bda678dc4e699b8f0f9a/charset_normalizer-3.4.5-cp312-cp312-manylinux_2_31_armv7l.whl", hash = "sha256:a118e2e0b5ae6b0120d5efa5f866e58f2bb826067a646431da4d6a2bdae7950e", size = 184715 },
{ url = "https://files.pythonhosted.org/packages/36/64/6b0ca95c44fddf692cd06d642b28f63009d0ce325fad6e9b2b4d0ef86a52/charset_normalizer-3.4.5-cp312-cp312-manylinux_2_31_riscv64.manylinux_2_39_riscv64.whl", hash = "sha256:754f96058e61a5e22e91483f823e07df16416ce76afa4ebf306f8e1d1296d43f", size = 193426 },
{ url = "https://files.pythonhosted.org/packages/50/bc/a730690d726403743795ca3f5bb2baf67838c5fea78236098f324b965e40/charset_normalizer-3.4.5-cp312-cp312-musllinux_1_2_aarch64.whl", hash = "sha256:0c300cefd9b0970381a46394902cd18eaf2aa00163f999590ace991989dcd0fc", size = 191780 },
{ url = "https://files.pythonhosted.org/packages/97/4f/6c0bc9af68222b22951552d73df4532b5be6447cee32d58e7e8c74ecbb7b/charset_normalizer-3.4.5-cp312-cp312-musllinux_1_2_armv7l.whl", hash = "sha256:c108f8619e504140569ee7de3f97d234f0fbae338a7f9f360455071ef9855a95", size = 185805 },
{ url = "https://files.pythonhosted.org/packages/dd/b9/a523fb9b0ee90814b503452b2600e4cbc118cd68714d57041564886e7325/charset_normalizer-3.4.5-cp312-cp312-musllinux_1_2_ppc64le.whl", hash = "sha256:d1028de43596a315e2720a9849ee79007ab742c06ad8b45a50db8cdb7ed4a82a", size = 208342 },
{ url = "https://files.pythonhosted.org/packages/4d/61/c59e761dee4464050713e50e27b58266cc8e209e518c0b378c1580c959ba/charset_normalizer-3.4.5-cp312-cp312-musllinux_1_2_riscv64.whl", hash = "sha256:19092dde50335accf365cce21998a1c6dd8eafd42c7b226eb54b2747cdce2fac", size = 193661 },
{ url = "https://files.pythonhosted.org/packages/1c/43/729fa30aad69783f755c5ad8649da17ee095311ca42024742701e202dc59/charset_normalizer-3.4.5-cp312-cp312-musllinux_1_2_s390x.whl", hash = "sha256:4354e401eb6dab9aed3c7b4030514328a6c748d05e1c3e19175008ca7de84fb1", size = 204819 },
{ url = "https://files.pythonhosted.org/packages/87/33/d9b442ce5a91b96fc0840455a9e49a611bbadae6122778d0a6a79683dd31/charset_normalizer-3.4.5-cp312-cp312-musllinux_1_2_x86_64.whl", hash = "sha256:a68766a3c58fde7f9aaa22b3786276f62ab2f594efb02d0a1421b6282e852e98", size = 198080 },
{ url = "https://files.pythonhosted.org/packages/56/5a/b8b5a23134978ee9885cee2d6995f4c27cc41f9baded0a9685eabc5338f0/charset_normalizer-3.4.5-cp312-cp312-win32.whl", hash = "sha256:1827734a5b308b65ac54e86a618de66f935a4f63a8a462ff1e19a6788d6c2262", size = 132630 },
{ url = "https://files.pythonhosted.org/packages/70/53/e44a4c07e8904500aec95865dc3f6464dc3586a039ef0df606eb3ac38e35/charset_normalizer-3.4.5-cp312-cp312-win_amd64.whl", hash = "sha256:728c6a963dfab66ef865f49286e45239384249672cd598576765acc2a640a636", size = 142856 },
{ url = "https://files.pythonhosted.org/packages/ea/aa/c5628f7cad591b1cf45790b7a61483c3e36cf41349c98af7813c483fd6e8/charset_normalizer-3.4.5-cp312-cp312-win_arm64.whl", hash = "sha256:75dfd1afe0b1647449e852f4fb428195a7ed0588947218f7ba929f6538487f02", size = 132982 },
{ url = "https://files.pythonhosted.org/packages/f5/48/9f34ec4bb24aa3fdba1890c1bddb97c8a4be1bd84ef5c42ac2352563ad05/charset_normalizer-3.4.5-cp313-cp313-macosx_10_13_universal2.whl", hash = "sha256:ac59c15e3f1465f722607800c68713f9fbc2f672b9eb649fe831da4019ae9b23", size = 280788 },
{ url = "https://files.pythonhosted.org/packages/0e/09/6003e7ffeb90cc0560da893e3208396a44c210c5ee42efff539639def59b/charset_normalizer-3.4.5-cp313-cp313-manylinux2014_aarch64.manylinux_2_17_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:165c7b21d19365464e8f70e5ce5e12524c58b48c78c1f5a57524603c1ab003f8", size = 188890 },
{ url = "https://files.pythonhosted.org/packages/42/1e/02706edf19e390680daa694d17e2b8eab4b5f7ac285e2a51168b4b22ee6b/charset_normalizer-3.4.5-cp313-cp313-manylinux2014_ppc64le.manylinux_2_17_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:28269983f25a4da0425743d0d257a2d6921ea7d9b83599d4039486ec5b9f911d", size = 206136 },
{ url = "https://files.pythonhosted.org/packages/c7/87/942c3def1b37baf3cf786bad01249190f3ca3d5e63a84f831e704977de1f/charset_normalizer-3.4.5-cp313-cp313-manylinux2014_s390x.manylinux_2_17_s390x.manylinux_2_28_s390x.whl", hash = "sha256:d27ce22ec453564770d29d03a9506d449efbb9fa13c00842262b2f6801c48cce", size = 202551 },
{ url = "https://files.pythonhosted.org/packages/94/0a/af49691938dfe175d71b8a929bd7e4ace2809c0c5134e28bc535660d5262/charset_normalizer-3.4.5-cp313-cp313-manylinux2014_x86_64.manylinux_2_17_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:0625665e4ebdddb553ab185de5db7054393af8879fb0c87bd5690d14379d6819", size = 195572 },
{ url = "https://files.pythonhosted.org/packages/20/ea/dfb1792a8050a8e694cfbde1570ff97ff74e48afd874152d38163d1df9ae/charset_normalizer-3.4.5-cp313-cp313-manylinux_2_31_armv7l.whl", hash = "sha256:c23eb3263356d94858655b3e63f85ac5d50970c6e8febcdde7830209139cc37d", size = 184438 },
{ url = "https://files.pythonhosted.org/packages/72/12/c281e2067466e3ddd0595bfaea58a6946765ace5c72dfa3edc2f5f118026/charset_normalizer-3.4.5-cp313-cp313-manylinux_2_31_riscv64.manylinux_2_39_riscv64.whl", hash = "sha256:e6302ca4ae283deb0af68d2fbf467474b8b6aedcd3dab4db187e07f94c109763", size = 193035 },
{ url = "https://files.pythonhosted.org/packages/ba/4f/3792c056e7708e10464bad0438a44708886fb8f92e3c3d29ec5e2d964d42/charset_normalizer-3.4.5-cp313-cp313-musllinux_1_2_aarch64.whl", hash = "sha256:e51ae7d81c825761d941962450f50d041db028b7278e7b08930b4541b3e45cb9", size = 191340 },
{ url = "https://files.pythonhosted.org/packages/e7/86/80ddba897127b5c7a9bccc481b0cd36c8fefa485d113262f0fe4332f0bf4/charset_normalizer-3.4.5-cp313-cp313-musllinux_1_2_armv7l.whl", hash = "sha256:597d10dec876923e5c59e48dbd366e852eacb2b806029491d307daea6b917d7c", size = 185464 },
{ url = "https://files.pythonhosted.org/packages/4d/00/b5eff85ba198faacab83e0e4b6f0648155f072278e3b392a82478f8b988b/charset_normalizer-3.4.5-cp313-cp313-musllinux_1_2_ppc64le.whl", hash = "sha256:5cffde4032a197bd3b42fd0b9509ec60fb70918d6970e4cc773f20fc9180ca67", size = 208014 },
{ url = "https://files.pythonhosted.org/packages/c8/11/d36f70be01597fd30850dde8a1269ebc8efadd23ba5785808454f2389bde/charset_normalizer-3.4.5-cp313-cp313-musllinux_1_2_riscv64.whl", hash = "sha256:2da4eedcb6338e2321e831a0165759c0c620e37f8cd044a263ff67493be8ffb3", size = 193297 },
{ url = "https://files.pythonhosted.org/packages/1a/1d/259eb0a53d4910536c7c2abb9cb25f4153548efb42800c6a9456764649c0/charset_normalizer-3.4.5-cp313-cp313-musllinux_1_2_s390x.whl", hash = "sha256:65a126fb4b070d05340a84fc709dd9e7c75d9b063b610ece8a60197a291d0adf", size = 204321 },
{ url = "https://files.pythonhosted.org/packages/84/31/faa6c5b9d3688715e1ed1bb9d124c384fe2fc1633a409e503ffe1c6398c1/charset_normalizer-3.4.5-cp313-cp313-musllinux_1_2_x86_64.whl", hash = "sha256:c7a80a9242963416bd81f99349d5f3fce1843c303bd404f204918b6d75a75fd6", size = 197509 },
{ url = "https://files.pythonhosted.org/packages/fd/a5/c7d9dd1503ffc08950b3260f5d39ec2366dd08254f0900ecbcf3a6197c7c/charset_normalizer-3.4.5-cp313-cp313-win32.whl", hash = "sha256:f1d725b754e967e648046f00c4facc42d414840f5ccc670c5670f59f83693e4f", size = 132284 },
{ url = "https://files.pythonhosted.org/packages/b9/0f/57072b253af40c8aa6636e6de7d75985624c1eb392815b2f934199340a89/charset_normalizer-3.4.5-cp313-cp313-win_amd64.whl", hash = "sha256:e37bd100d2c5d3ba35db9c7c5ba5a9228cbcffe5c4778dc824b164e5257813d7", size = 142630 },
{ url = "https://files.pythonhosted.org/packages/31/41/1c4b7cc9f13bd9d369ce3bc993e13d374ce25fa38a2663644283ecf422c1/charset_normalizer-3.4.5-cp313-cp313-win_arm64.whl", hash = "sha256:93b3b2cc5cf1b8743660ce77a4f45f3f6d1172068207c1defc779a36eea6bb36", size = 133254 },
{ url = "https://files.pythonhosted.org/packages/43/be/0f0fd9bb4a7fa4fb5067fb7d9ac693d4e928d306f80a0d02bde43a7c4aee/charset_normalizer-3.4.5-cp314-cp314-macosx_10_15_universal2.whl", hash = "sha256:8197abe5ca1ffb7d91e78360f915eef5addff270f8a71c1fc5be24a56f3e4873", size = 280232 },
{ url = "https://files.pythonhosted.org/packages/28/02/983b5445e4bef49cd8c9da73a8e029f0825f39b74a06d201bfaa2e55142a/charset_normalizer-3.4.5-cp314-cp314-manylinux2014_aarch64.manylinux_2_17_aarch64.manylinux_2_28_aarch64.whl", hash = "sha256:a2aecdb364b8a1802afdc7f9327d55dad5366bc97d8502d0f5854e50712dbc5f", size = 189688 },
{ url = "https://files.pythonhosted.org/packages/d0/88/152745c5166437687028027dc080e2daed6fe11cfa95a22f4602591c42db/charset_normalizer-3.4.5-cp314-cp314-manylinux2014_ppc64le.manylinux_2_17_ppc64le.manylinux_2_28_ppc64le.whl", hash = "sha256:a66aa5022bf81ab4b1bebfb009db4fd68e0c6d4307a1ce5ef6a26e5878dfc9e4", size = 206833 },
{ url = "https://files.pythonhosted.org/packages/cb/0f/ebc15c8b02af2f19be9678d6eed115feeeccc45ce1f4b098d986c13e8769/charset_normalizer-3.4.5-cp314-cp314-manylinux2014_s390x.manylinux_2_17_s390x.manylinux_2_28_s390x.whl", hash = "sha256:d77f97e515688bd615c1d1f795d540f32542d514242067adcb8ef532504cb9ee", size = 202879 },
{ url = "https://files.pythonhosted.org/packages/38/9c/71336bff6934418dc8d1e8a1644176ac9088068bc571da612767619c97b3/charset_normalizer-3.4.5-cp314-cp314-manylinux2014_x86_64.manylinux_2_17_x86_64.manylinux_2_28_x86_64.whl", hash = "sha256:01a1ed54b953303ca7e310fafe0fe347aab348bd81834a0bcd602eb538f89d66", size = 195764 },
{ url = "https://files.pythonhosted.org/packages/b7/95/ce92fde4f98615661871bc282a856cf9b8a15f686ba0af012984660d480b/charset_normalizer-3.4.5-cp314-cp314-manylinux_2_31_armv7l.whl", hash = "sha256:b2d37d78297b39a9eb9eb92c0f6df98c706467282055419df141389b23f93362", size = 183728 },
{ url = "https://files.pythonhosted.org/packages/1c/e7/f5b4588d94e747ce45ae680f0f242bc2d98dbd4eccfab73e6160b6893893/charset_normalizer-3.4.5-cp314-cp314-manylinux_2_31_riscv64.manylinux_2_39_riscv64.whl", hash = "sha256:e71bbb595973622b817c042bd943c3f3667e9c9983ce3d205f973f486fec98a7", size = 192937 },
{ url = "https://files.pythonhosted.org/packages/f9/29/9d94ed6b929bf9f48bf6ede6e7474576499f07c4c5e878fb186083622716/charset_normalizer-3.4.5-cp314-cp314-musllinux_1_2_aarch64.whl", hash = "sha256:4cd966c2559f501c6fd69294d082c2934c8dd4719deb32c22961a5ac6db0df1d", size = 192040 },
{ url = "https://files.pythonhosted.org/packages/15/d2/1a093a1cf827957f9445f2fe7298bcc16f8fc5e05c1ed2ad1af0b239035e/charset_normalizer-3.4.5-cp314-cp314-musllinux_1_2_armv7l.whl", hash = "sha256:d5e52d127045d6ae01a1e821acfad2f3a1866c54d0e837828538fabe8d9d1bd6", size = 184107 },
{ url = "https://files.pythonhosted.org/packages/0f/7d/82068ce16bd36135df7b97f6333c5d808b94e01d4599a682e2337ed5fd14/charset_normalizer-3.4.5-cp314-cp314-musllinux_1_2_ppc64le.whl", hash = "sha256:30a2b1a48478c3428d047ed9690d57c23038dac838a87ad624c85c0a78ebeb39", size = 208310 },
{ url = "https://files.pythonhosted.org/packages/84/4e/4dfb52307bb6af4a5c9e73e482d171b81d36f522b21ccd28a49656baa680/charset_normalizer-3.4.5-cp314-cp314-musllinux_1_2_riscv64.whl", hash = "sha256:d8ed79b8f6372ca4254955005830fd61c1ccdd8c0fac6603e2c145c61dd95db6", size = 192918 },
{ url = "https://files.pythonhosted.org/packages/08/a4/159ff7da662cf7201502ca89980b8f06acf3e887b278956646a8aeb178ab/charset_normalizer-3.4.5-cp314-cp314-musllinux_1_2_s390x.whl", hash = "sha256:c5af897b45fa606b12464ccbe0014bbf8c09191e0a66aab6aa9d5cf6e77e0c94", size = 204615 },
{ url = "https://files.pythonhosted.org/packages/d6/62/0dd6172203cb6b429ffffc9935001fde42e5250d57f07b0c28c6046deb6b/charset_normalizer-3.4.5-cp314-cp314-musllinux_1_2_x86_64.whl", hash = "sha256:1088345bcc93c58d8d8f3d783eca4a6e7a7752bbff26c3eee7e73c597c191c2e", size = 197784 },
{ url = "https://files.pythonhosted.org/packages/c7/5e/1aab5cb737039b9c59e63627dc8bbc0d02562a14f831cc450e5f91d84ce1/charset_normalizer-3.4.5-cp314-cp314-win32.whl", hash = "sha256:ee57b926940ba00bca7ba7041e665cc956e55ef482f851b9b65acb20d867e7a2", size = 133009 },
{ url = "https://files.pythonhosted.org/packages/40/65/e7c6c77d7aaa4c0d7974f2e403e17f0ed2cb0fc135f77d686b916bf1eead/charset_normalizer-3.4.5-cp314-cp314-win_amd64.whl", hash = "sha256:4481e6da1830c8a1cc0b746b47f603b653dadb690bcd851d039ffaefe70533aa", size = 143511 },
{ url = "https://files.pythonhosted.org/packages/ba/91/52b0841c71f152f563b8e072896c14e3d83b195c188b338d3cc2e582d1d4/charset_normalizer-3.4.5-cp314-cp314-win_arm64.whl", hash = "sha256:97ab7787092eb9b50fb47fa04f24c75b768a606af1bcba1957f07f128a7219e4", size = 133775 },
{ url = "https://files.pythonhosted.org/packages/c5/60/3a621758945513adfd4db86827a5bafcc615f913dbd0b4c2ed64a65731be/charset_normalizer-3.4.5-py3-none-any.whl", hash = "sha256:9db5e3fcdcee89a78c04dffb3fe33c79f77bd741a624946db2591c81b2fc85b0", size = 55455 },
]
[[package]]
name = "idna"
version = "3.11"
source = { registry = "https://pypi.org/simple" }
sdist = { url = "https://files.pythonhosted.org/packages/6f/6d/0703ccc57f3a7233505399edb88de3cbd678da106337b9fcde432b65ed60/idna-3.11.tar.gz", hash = "sha256:795dafcc9c04ed0c1fb032c2aa73654d8e8c5023a7df64a53f39190ada629902", size = 194582 }
wheels = [
{ url = "https://files.pythonhosted.org/packages/0e/61/66938bbb5fc52dbdf84594873d5b51fb1f7c7794e9c0f5bd885f30bc507b/idna-3.11-py3-none-any.whl", hash = "sha256:771a87f49d9defaf64091e6e6fe9c18d4833f140bd19464795bc32d966ca37ea", size = 71008 },
]
[[package]]
name = "requests"
version = "2.32.5"
source = { registry = "https://pypi.org/simple" }
dependencies = [
{ name = "certifi" },
{ name = "charset-normalizer" },
{ name = "idna" },
{ name = "urllib3" },
]
sdist = { url = "https://files.pythonhosted.org/packages/c9/74/b3ff8e6c8446842c3f5c837e9c3dfcfe2018ea6ecef224c710c85ef728f4/requests-2.32.5.tar.gz", hash = "sha256:dbba0bac56e100853db0ea71b82b4dfd5fe2bf6d3754a8893c3af500cec7d7cf", size = 134517 }
wheels = [
{ url = "https://files.pythonhosted.org/packages/1e/db/4254e3eabe8020b458f1a747140d32277ec7a271daf1d235b70dc0b4e6e3/requests-2.32.5-py3-none-any.whl", hash = "sha256:2462f94637a34fd532264295e186976db0f5d453d1cdd31473c85a6a161affb6", size = 64738 },
]
[[package]]
name = "urllib3"
version = "2.6.3"
source = { registry = "https://pypi.org/simple" }
sdist = { url = "https://files.pythonhosted.org/packages/c7/24/5f1b3bdffd70275f6661c76461e25f024d5a38a46f04aaca912426a2b1d3/urllib3-2.6.3.tar.gz", hash = "sha256:1b62b6884944a57dbe321509ab94fd4d3b307075e0c2eae991ac71ee15ad38ed", size = 435556 }
wheels = [
{ url = "https://files.pythonhosted.org/packages/39/08/aaaad47bc4e9dc8c725e68f9d04865dbcb2052843ff09c97b08904852d84/urllib3-2.6.3-py3-none-any.whl", hash = "sha256:bf272323e553dfb2e87d9bfd225ca7b0f467b919d7bbd355436d3fd37cb0acd4", size = 131584 },
]