0.6.4-thumb-upgrade
Some checks failed
Deploy / deploy (push) Has been skipped
CI / lint (push) Successful in 1m53s
CI / test (push) Failing after 9m28s

This commit is contained in:
2025-09-03 10:21:17 +03:00
parent f0b327a99a
commit ae0fc9a18d
15 changed files with 1180 additions and 202 deletions

View File

@@ -1,10 +1,10 @@
use redis::{Client, AsyncCommands};
use redis::{AsyncCommands, Client};
use std::env;
#[tokio::test]
async fn test_redis_url_parsing() {
// Тестируем различные форматы Redis URL
let test_urls = vec![
// Простой URL без пароля
"redis://localhost:6379",
@@ -27,24 +27,36 @@ async fn test_redis_url_parsing() {
for url in test_urls {
// Парсим URL для детального вывода
if let Ok(parsed) = url::Url::parse(url) {
println!("Testing Redis URL: {}", url.replace(&url.split('@').nth(0).unwrap_or(""), "***"));
println!(
"Testing Redis URL: {}",
url.replace(&url.split('@').nth(0).unwrap_or(""), "***")
);
println!(" Host: {}", parsed.host_str().unwrap_or("none"));
println!(" Port: {}", parsed.port().unwrap_or(0));
println!(" Username: '{}'", parsed.username());
println!(" Password: '{}'", if parsed.password().is_some() { "***" } else { "none" });
println!(
" Password: '{}'",
if parsed.password().is_some() {
"***"
} else {
"none"
}
);
} else {
println!("Testing Redis URL: {}", url);
}
match Client::open(url) {
Ok(client) => {
println!("✅ URL parsed successfully");
// Попробуем подключиться (с коротким таймаутом)
match tokio::time::timeout(
std::time::Duration::from_secs(2),
client.get_multiplexed_async_connection()
).await {
client.get_multiplexed_async_connection(),
)
.await
{
Ok(Ok(_)) => println!("✅ Connection successful"),
Ok(Err(e)) => println!("❌ Connection failed: {}", e),
Err(_) => println!("⏰ Connection timeout"),
@@ -60,35 +72,48 @@ async fn test_redis_url_parsing() {
#[tokio::test]
async fn test_redis_connection_with_env() {
// Тестируем с реальным REDIS_URL из окружения
// Тестируем с реальным REDIS_URL из окружения
if let Ok(redis_url) = env::var("REDIS_URL") {
println!("Testing with real REDIS_URL: {}",
redis_url.replace(&redis_url.split('@').nth(0).unwrap_or(""), "***"));
println!(
"Testing with real REDIS_URL: {}",
redis_url.replace(&redis_url.split('@').nth(0).unwrap_or(""), "***")
);
// Парсим реальный URL для детального вывода
if let Ok(parsed) = url::Url::parse(&redis_url) {
println!(" Host: {}", parsed.host_str().unwrap_or("none"));
println!(" Port: {}", parsed.port().unwrap_or(0));
println!(" Username: '{}'", parsed.username());
println!(" Password: '{}'", if parsed.password().is_some() { "***" } else { "none" });
println!(
" Password: '{}'",
if parsed.password().is_some() {
"***"
} else {
"none"
}
);
}
match Client::open(redis_url) {
Ok(client) => {
println!("✅ Real URL parsed successfully");
match tokio::time::timeout(
std::time::Duration::from_secs(5),
client.get_multiplexed_async_connection()
).await {
client.get_multiplexed_async_connection(),
)
.await
{
Ok(Ok(mut conn)) => {
println!("✅ Real connection successful");
// Попробуем выполнить простую команду
match tokio::time::timeout(
std::time::Duration::from_secs(2),
conn.ping::<String>()
).await {
conn.ping::<String>(),
)
.await
{
Ok(Ok(result)) => println!("✅ PING successful: {}", result),
Ok(Err(e)) => println!("❌ PING failed: {}", e),
Err(_) => println!("⏰ PING timeout"),
@@ -111,19 +136,28 @@ async fn test_redis_connection_with_env() {
fn test_redis_url_components() {
// Тестируем парсинг компонентов URL
let test_url = "redis://:dbc5f9f9007c555e209964454c9d6abecae5f1db72e490acd5c94354dc012282@dokku-redis-discoursio-redis:6379";
if let Ok(parsed) = url::Url::parse(test_url) {
println!("✅ URL parsed successfully");
println!(" Scheme: {}", parsed.scheme());
println!(" Host: {}", parsed.host_str().unwrap_or("none"));
println!(" Port: {}", parsed.port().unwrap_or(0));
println!(" Username: '{}'", parsed.username());
println!(" Password: {}", if parsed.password().is_some() { "***" } else { "none" });
println!(
" Password: {}",
if parsed.password().is_some() {
"***"
} else {
"none"
}
);
println!(" Path: {}", parsed.path());
// Проверяем, что пустое имя пользователя означает дефолтное 'redis'
if parsed.username().is_empty() && parsed.password().is_some() {
println!(" ⚠️ Empty username with password - Redis client should use default 'redis' user");
println!(
" ⚠️ Empty username with password - Redis client should use default 'redis' user"
);
}
} else {
println!("❌ URL parsing failed");
@@ -134,22 +168,38 @@ fn test_redis_url_components() {
async fn test_redis_default_username_behavior() {
// Тестируем поведение Redis client с пустым именем пользователя
println!("Testing Redis default username behavior...");
let test_cases = vec![
("redis://:password@localhost:6379", "Empty username with password"),
("redis://redis:password@localhost:6379", "Explicit redis username"),
(
"redis://:password@localhost:6379",
"Empty username with password",
),
(
"redis://redis:password@localhost:6379",
"Explicit redis username",
),
("redis://:@localhost:6379", "Empty username and password"),
("redis://localhost:6379", "No authentication"),
];
for (url, description) in test_cases {
println!("\n--- {} ---", description);
println!("URL: {}", url.replace(&url.split('@').nth(0).unwrap_or(""), "***"));
println!(
"URL: {}",
url.replace(&url.split('@').nth(0).unwrap_or(""), "***")
);
if let Ok(parsed) = url::Url::parse(url) {
println!(" Parsed Username: '{}'", parsed.username());
println!(" Parsed Password: {}", if parsed.password().is_some() { "***" } else { "none" });
println!(
" Parsed Password: {}",
if parsed.password().is_some() {
"***"
} else {
"none"
}
);
// Redis client поведение:
// - Если username пустой, но есть password -> использует дефолтное имя 'redis'
// - Если username и password пустые -> без аутентификации