mirror of
https://github.com/OrcaSlicer/OrcaSlicer.git
synced 2026-05-14 00:52:04 +00:00
Fix inconsistent displayed name (#13645)
* Add get_json_string_field helper Introduce get_json_string_field in OrcaCloudServiceAgent.cpp to safely extract string fields from JSON objects. * Add resolve_display_name helper Introduce resolve_display_name to normalize provider metadata labels for the UI. The helper returns the first non-empty value from display_name, nickname, full_name, name, falling back to username, resolving human-facing label across varying provider payloads. * Replace safe_str anonymous function Replace get_json_string_field for better readability. * Replace resolution flow for nickname with function Consolidate both flows into one function for easier maintenance and more consistency. * Update OrcaCloudServiceAgent.hpp * Add OrcaCloudServiceAgent display name tests Add unit tests verifying OrcaCloudServiceAgent resolves a user's display name from various session JSON shapes.
This commit is contained in:
@@ -74,6 +74,32 @@ constexpr const char* SECRET_STORE_SERVICE = "OrcaSlicer/Auth";
|
||||
constexpr const char* SECRET_STORE_USER = "orca_refresh_token";
|
||||
constexpr std::chrono::seconds TOKEN_REFRESH_SKEW{900}; // 15 minutes
|
||||
|
||||
// Return a JSON field only when it is present as a string. Missing or non-string values normalize to empty.
|
||||
std::string get_json_string_field(const json& j, const std::string& key)
|
||||
{
|
||||
if (j.contains(key) && j[key].is_string()) {
|
||||
return j[key].get<std::string>();
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
// Resolve the human-facing UI label from provider metadata.
|
||||
std::string resolve_display_name(
|
||||
const std::string& display_name,
|
||||
const std::string& nickname,
|
||||
const std::string& full_name,
|
||||
const std::string& name,
|
||||
const std::string& username)
|
||||
{
|
||||
// Providers and payload shapes do not all use the same display-name field.
|
||||
// Fallback sequence: display_name -> nickname -> full_name -> name
|
||||
if (!display_name.empty()) return display_name;
|
||||
if (!nickname.empty()) return nickname;
|
||||
if (!full_name.empty()) return full_name;
|
||||
if (!name.empty()) return name;
|
||||
return username;
|
||||
}
|
||||
|
||||
std::string generate_uuid_for_setting_id(const std::string& name, const std::string& user_id = "")
|
||||
{
|
||||
if (name.empty()) {
|
||||
@@ -1667,47 +1693,43 @@ bool OrcaCloudServiceAgent::set_user_session(const std::string& token,
|
||||
|
||||
bool OrcaCloudServiceAgent::set_user_session(const json& session_json, bool notify_login)
|
||||
{
|
||||
auto safe_str = [](const json& j, const std::string& key) -> std::string {
|
||||
if (j.contains(key) && j[key].is_string()) return j[key].get<std::string>();
|
||||
return "";
|
||||
};
|
||||
|
||||
std::string access_token = safe_str(session_json, "access_token");
|
||||
std::string access_token = get_json_string_field(session_json, "access_token");
|
||||
if (access_token.empty()) {
|
||||
access_token = safe_str(session_json, "token");
|
||||
access_token = get_json_string_field(session_json, "token");
|
||||
}
|
||||
std::string refresh_token = safe_str(session_json, "refresh_token");
|
||||
std::string refresh_token = get_json_string_field(session_json, "refresh_token");
|
||||
|
||||
std::string user_id, username, nickname, avatar;
|
||||
if (session_json.contains("user") && session_json["user"].is_object()) {
|
||||
// Nested format (Orca cloud / GoTrue response)
|
||||
const auto& user = session_json["user"];
|
||||
user_id = safe_str(user, "id");
|
||||
user_id = get_json_string_field(user, "id");
|
||||
|
||||
if (user.contains("user_metadata") && user["user_metadata"].is_object()) {
|
||||
|
||||
const auto& meta = user["user_metadata"];
|
||||
username = safe_str(meta, "username"); // Orca Cloud's unique username
|
||||
username = get_json_string_field(meta, "username"); // Orca Cloud's unique username
|
||||
|
||||
nickname = safe_str(meta, "display_name"); // Orca Cloud's primary display name field
|
||||
// Fallback to different name from different providers if display_name is not set
|
||||
if (nickname.empty())
|
||||
nickname = safe_str(meta, "full_name");
|
||||
if (nickname.empty())
|
||||
nickname = safe_str(meta, "name");
|
||||
if (nickname.empty())
|
||||
nickname = username;
|
||||
|
||||
avatar = safe_str(meta, "avatar_url");
|
||||
// Orca Cloud's primary display name field is display_name.
|
||||
// Fallback to different names from different providers if display_name is not set.
|
||||
nickname = resolve_display_name(
|
||||
get_json_string_field(meta, "display_name"),
|
||||
get_json_string_field(meta, "nickname"),
|
||||
get_json_string_field(meta, "full_name"),
|
||||
get_json_string_field(meta, "name"),
|
||||
username);
|
||||
avatar = get_json_string_field(meta, "avatar_url");
|
||||
}
|
||||
} else {
|
||||
// Flat format (WebView direct token flow)
|
||||
user_id = safe_str(session_json, "user_id");
|
||||
username = safe_str(session_json, "username");
|
||||
nickname = safe_str(session_json, "display_name");
|
||||
if(nickname.empty())
|
||||
nickname = safe_str(session_json, "nickname");
|
||||
|
||||
avatar = safe_str(session_json, "avatar");
|
||||
user_id = get_json_string_field(session_json, "user_id");
|
||||
username = get_json_string_field(session_json, "username");
|
||||
nickname = resolve_display_name(
|
||||
get_json_string_field(session_json, "display_name"),
|
||||
get_json_string_field(session_json, "nickname"),
|
||||
get_json_string_field(session_json, "full_name"),
|
||||
get_json_string_field(session_json, "name"),
|
||||
username);
|
||||
avatar = get_json_string_field(session_json, "avatar");
|
||||
}
|
||||
|
||||
if (access_token.empty() || user_id.empty()) {
|
||||
|
||||
@@ -88,8 +88,8 @@ public:
|
||||
std::string access_token;
|
||||
std::string refresh_token;
|
||||
std::string user_id;
|
||||
// Orca auth semantics: user_name is unique orca cloud username(orca_xxxxx), user_nickname is
|
||||
// the display name shown in the UI when available.
|
||||
// Orca auth semantics: user_name is the unique Orca Cloud username (orca_xxxxx),
|
||||
// user_nickname is the display name shown in the UI when available.
|
||||
std::string user_name;
|
||||
std::string user_nickname;
|
||||
std::string user_avatar;
|
||||
@@ -276,13 +276,14 @@ public:
|
||||
bool refresh_now(const std::string& refresh_token, const std::string& reason, bool async = false);
|
||||
bool refresh_session_with_token(const std::string& refresh_token);
|
||||
|
||||
// Session state helpers
|
||||
// Session state helpers. nickname is the human-facing UI label after provider fallback resolution.
|
||||
bool set_user_session(const std::string& token,
|
||||
const std::string& user_id,
|
||||
const std::string& username,
|
||||
const std::string& nickname,
|
||||
const std::string& avatar,
|
||||
const std::string& refresh_token = "");
|
||||
// Accepts either nested Orca cloud / GoTrue session JSON or flat WebView token JSON.
|
||||
bool set_user_session(const nlohmann::json& session_json, bool notify_login = true);
|
||||
void clear_session();
|
||||
|
||||
|
||||
@@ -1,6 +1,47 @@
|
||||
#include <catch2/catch_all.hpp>
|
||||
|
||||
#include "slic3r/Utils/Http.hpp"
|
||||
#include "slic3r/Utils/OrcaCloudServiceAgent.hpp"
|
||||
|
||||
#include <wx/init.h>
|
||||
|
||||
namespace {
|
||||
|
||||
struct WxFixture {
|
||||
WxFixture() { REQUIRE(initializer.IsOk()); }
|
||||
|
||||
wxInitializer initializer;
|
||||
};
|
||||
|
||||
nlohmann::json flat_session_json(const nlohmann::json& fields)
|
||||
{
|
||||
nlohmann::json session = {
|
||||
{"access_token", "test-token"},
|
||||
{"user_id", "test-user-id"}
|
||||
};
|
||||
session.update(fields);
|
||||
return session;
|
||||
}
|
||||
|
||||
nlohmann::json nested_session_json(const nlohmann::json& metadata)
|
||||
{
|
||||
return {
|
||||
{"access_token", "test-token"},
|
||||
{"user", {
|
||||
{"id", "test-user-id"},
|
||||
{"user_metadata", metadata}
|
||||
}}
|
||||
};
|
||||
}
|
||||
|
||||
std::string resolved_display_name(const nlohmann::json& session)
|
||||
{
|
||||
Slic3r::OrcaCloudServiceAgent agent("");
|
||||
REQUIRE(agent.set_user_session(session, false));
|
||||
return agent.get_user_nickname();
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
TEST_CASE("Check SSL certificates paths", "[Http][NotWorking]") {
|
||||
|
||||
@@ -20,6 +61,62 @@ TEST_CASE("Check SSL certificates paths", "[Http][NotWorking]") {
|
||||
REQUIRE(status == 200);
|
||||
}
|
||||
|
||||
TEST_CASE_METHOD(WxFixture, "Orca cloud flat session resolves display name consistently", "[OrcaCloudServiceAgent]")
|
||||
{
|
||||
CHECK(resolved_display_name(flat_session_json({
|
||||
{"username", "orca_username"},
|
||||
{"display_name", "Display Name"},
|
||||
{"nickname", "Nickname"}
|
||||
})) == "Display Name");
|
||||
|
||||
CHECK(resolved_display_name(flat_session_json({
|
||||
{"username", "orca_username"},
|
||||
{"nickname", "Nickname"}
|
||||
})) == "Nickname");
|
||||
|
||||
CHECK(resolved_display_name(flat_session_json({
|
||||
{"username", "orca_username"},
|
||||
{"full_name", "Full Name"}
|
||||
})) == "Full Name");
|
||||
|
||||
CHECK(resolved_display_name(flat_session_json({
|
||||
{"username", "orca_username"},
|
||||
{"name", "Provider Name"}
|
||||
})) == "Provider Name");
|
||||
|
||||
CHECK(resolved_display_name(flat_session_json({
|
||||
{"username", "orca_username"}
|
||||
})) == "orca_username");
|
||||
}
|
||||
|
||||
TEST_CASE_METHOD(WxFixture, "Orca cloud nested session resolves display name consistently", "[OrcaCloudServiceAgent]")
|
||||
{
|
||||
CHECK(resolved_display_name(nested_session_json({
|
||||
{"username", "orca_username"},
|
||||
{"display_name", "Display Name"},
|
||||
{"nickname", "Nickname"}
|
||||
})) == "Display Name");
|
||||
|
||||
CHECK(resolved_display_name(nested_session_json({
|
||||
{"username", "orca_username"},
|
||||
{"nickname", "Nickname"}
|
||||
})) == "Nickname");
|
||||
|
||||
CHECK(resolved_display_name(nested_session_json({
|
||||
{"username", "orca_username"},
|
||||
{"full_name", "Full Name"}
|
||||
})) == "Full Name");
|
||||
|
||||
CHECK(resolved_display_name(nested_session_json({
|
||||
{"username", "orca_username"},
|
||||
{"name", "Provider Name"}
|
||||
})) == "Provider Name");
|
||||
|
||||
CHECK(resolved_display_name(nested_session_json({
|
||||
{"username", "orca_username"}
|
||||
})) == "orca_username");
|
||||
}
|
||||
|
||||
TEST_CASE("Http digest authentication", "[Http][NotWorking]") {
|
||||
Slic3r::Http g = Slic3r::Http::get("https://httpbingo.org/digest-auth/auth/guest/guest");
|
||||
|
||||
|
||||
Reference in New Issue
Block a user