Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Friends system for app #2958

Merged
merged 4 commits into from
Nov 27, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
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
5 changes: 3 additions & 2 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
SteamIcon,
GitLabIcon,
} from '@/assets/external'
import { login, login_2fa, create_account, login_pass } from '@/helpers/mr_auth.js'
import { login } from '@/helpers/mr_auth.js'
import { handleError, useNotifications } from '@/store/state.js'
import { ref } from 'vue'
import { handleSevereError } from '@/store/error.js'
Expand Down Expand Up @@ -71,8 +71,8 @@
const confirmPassword = ref('')
const subscribe = ref(true)

async function signInOauth(provider) {

Check failure on line 74 in apps/app-frontend/src/components/ui/tutorial/ModrinthLoginScreen.vue

View workflow job for this annotation

GitHub Actions / Build, Test, and Lint

'provider' is defined but never used. Allowed unused args must match /^_/u
const creds = await login(provider).catch(handleSevereError)
const creds = await login().catch(handleSevereError)

if (creds && creds.type === 'two_factor_required') {
twoFactorFlow.value = creds.flow
Expand Down
22 changes: 2 additions & 20 deletions apps/app-frontend/src/helpers/mr_auth.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,26 +5,8 @@
*/
import { invoke } from '@tauri-apps/api/core'

export async function login(provider) {
return await invoke('modrinth_auth_login', { provider })
}

export async function login_pass(username, password, challenge) {
return await invoke('plugin:mr-auth|login_pass', { username, password, challenge })
}

export async function login_2fa(code, flow) {
return await invoke('plugin:mr-auth|login_2fa', { code, flow })
}

export async function create_account(username, email, password, challenge, signUpNewsletter) {
return await invoke('plugin:mr-auth|create_account', {
username,
email,
password,
challenge,
signUpNewsletter,
})
export async function login() {
return await invoke('plugin:mr-auth|modrinth_login')
}

export async function logout() {
Expand Down
8 changes: 1 addition & 7 deletions apps/app/build.rs
Original file line number Diff line number Diff line change
Expand Up @@ -102,13 +102,7 @@ fn main() {
.plugin(
"mr-auth",
InlinedPlugin::new()
.commands(&[
"login_pass",
"login_2fa",
"create_account",
"logout",
"get",
])
.commands(&["modrinth_login", "logout", "get"])
.default_permission(
DefaultPermissionRule::AllowAllCommands,
),
Expand Down
2 changes: 1 addition & 1 deletion apps/app/gen/schemas/acl-manifests.json

Large diffs are not rendered by default.

10 changes: 10 additions & 0 deletions apps/app/gen/schemas/desktop-schema.json
Original file line number Diff line number Diff line change
Expand Up @@ -2410,6 +2410,11 @@
"type": "string",
"const": "mr-auth:allow-logout"
},
{
"description": "Enables the modrinth_login command without any pre-configured scope.",
"type": "string",
"const": "mr-auth:allow-modrinth-login"
},
{
"description": "Denies the create_account command without any pre-configured scope.",
"type": "string",
Expand All @@ -2435,6 +2440,11 @@
"type": "string",
"const": "mr-auth:deny-logout"
},
{
"description": "Denies the modrinth_login command without any pre-configured scope.",
"type": "string",
"const": "mr-auth:deny-modrinth-login"
},
{
"description": "This permission set configures which\noperating system information are available\nto gather from the frontend.\n\n#### Granted Permissions\n\nAll information except the host name are available.\n\n",
"type": "string",
Expand Down
10 changes: 10 additions & 0 deletions apps/app/gen/schemas/macOS-schema.json
Original file line number Diff line number Diff line change
Expand Up @@ -2410,6 +2410,11 @@
"type": "string",
"const": "mr-auth:allow-logout"
},
{
"description": "Enables the modrinth_login command without any pre-configured scope.",
"type": "string",
"const": "mr-auth:allow-modrinth-login"
},
{
"description": "Denies the create_account command without any pre-configured scope.",
"type": "string",
Expand All @@ -2435,6 +2440,11 @@
"type": "string",
"const": "mr-auth:deny-logout"
},
{
"description": "Denies the modrinth_login command without any pre-configured scope.",
"type": "string",
"const": "mr-auth:deny-modrinth-login"
},
{
"description": "This permission set configures which\noperating system information are available\nto gather from the frontend.\n\n#### Granted Permissions\n\nAll information except the host name are available.\n\n",
"type": "string",
Expand Down
79 changes: 21 additions & 58 deletions apps/app/src/api/mr_auth.rs
Original file line number Diff line number Diff line change
@@ -1,27 +1,20 @@
use crate::api::Result;
use chrono::{Duration, Utc};
use tauri::plugin::TauriPlugin;
use tauri::{Manager, UserAttentionType};
use tauri::{Manager, Runtime, UserAttentionType};
use theseus::prelude::*;

pub fn init<R: tauri::Runtime>() -> TauriPlugin<R> {
tauri::plugin::Builder::new("mr-auth")
.invoke_handler(tauri::generate_handler![
login_pass,
login_2fa,
create_account,
logout,
get,
])
.invoke_handler(tauri::generate_handler![modrinth_login, logout, get,])
.build()
}

#[tauri::command]
pub async fn modrinth_auth_login(
app: tauri::AppHandle,
provider: &str,
) -> Result<Option<ModrinthCredentialsResult>> {
let redirect_uri = mr_auth::authenticate_begin_flow(provider);
pub async fn modrinth_login<R: Runtime>(
app: tauri::AppHandle<R>,
) -> Result<Option<ModrinthCredentials>> {
let redirect_uri = mr_auth::authenticate_begin_flow();

let start = Utc::now();

Expand All @@ -39,6 +32,10 @@ pub async fn modrinth_auth_login(
.as_error()
})?),
)
.min_inner_size(420.0, 632.0)
.inner_size(420.0, 632.0)
.max_inner_size(420.0, 632.0)
.zoom_hotkeys_enabled(false)
.title("Sign into Modrinth")
.always_on_top(true)
.center()
Expand All @@ -55,23 +52,21 @@ pub async fn modrinth_auth_login(
if window
.url()?
.as_str()
.starts_with("https://launcher-files.modrinth.com/detect.txt")
.starts_with("https://launcher-files.modrinth.com")
{
let query = window
.url()?
.query_pairs()
.map(|(key, val)| {
(
key.to_string(),
serde_json::Value::String(val.to_string()),
)
})
.collect();
let url = window.url()?;

let code = url.query_pairs().find(|(key, _)| key == "code");

window.close()?;

let val = mr_auth::authenticate_finish_flow(query).await?;
return if let Some((_, code)) = code {
let val = mr_auth::authenticate_finish_flow(&code).await?;

return Ok(Some(val));
Ok(Some(val))
} else {
Ok(None)
};
}

tokio::time::sleep(std::time::Duration::from_millis(50)).await;
Expand All @@ -81,38 +76,6 @@ pub async fn modrinth_auth_login(
Ok(None)
}

#[tauri::command]
pub async fn login_pass(
username: &str,
password: &str,
challenge: &str,
) -> Result<ModrinthCredentialsResult> {
Ok(theseus::mr_auth::login_password(username, password, challenge).await?)
}

#[tauri::command]
pub async fn login_2fa(code: &str, flow: &str) -> Result<ModrinthCredentials> {
Ok(theseus::mr_auth::login_2fa(code, flow).await?)
}

#[tauri::command]
pub async fn create_account(
username: &str,
email: &str,
password: &str,
challenge: &str,
sign_up_newsletter: bool,
) -> Result<ModrinthCredentials> {
Ok(theseus::mr_auth::create_account(
username,
email,
password,
challenge,
sign_up_newsletter,
)
.await?)
}

#[tauri::command]
pub async fn logout() -> Result<()> {
Ok(theseus::mr_auth::logout().await?)
Expand Down
1 change: 0 additions & 1 deletion apps/app/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -264,7 +264,6 @@ fn main() {
initialize_state,
is_dev,
toggle_decorations,
api::mr_auth::modrinth_auth_login,
show_window,
restart_app,
]);
Expand Down
6 changes: 3 additions & 3 deletions apps/app/tauri.conf.json
Original file line number Diff line number Diff line change
Expand Up @@ -91,14 +91,14 @@
"capabilities": ["ads", "core", "plugins"],
"csp": {
"default-src": "'self' customprotocol: asset:",
"connect-src": "ipc: http://ipc.localhost https://modrinth.com https://*.modrinth.com https://*.posthog.com https://*.sentry.io https://*.cloudflare.com https://api.mclo.gs https://cmp.inmobi.com",
"connect-src": "ipc: http://ipc.localhost https://modrinth.com https://*.modrinth.com https://*.posthog.com https://*.sentry.io https://api.mclo.gs",
"font-src": [
"https://cdn-raw.modrinth.com/fonts/inter/"
],
"img-src": "https: 'unsafe-inline' 'self' asset: http://asset.localhost blob: data:",
"style-src": "'unsafe-inline' 'self'",
"script-src": "https://cmp.inmobi.com https://*.cloudflare.com https://*.posthog.com 'self'",
"frame-src": "https://*.cloudflare.com https://www.youtube.com https://www.youtube-nocookie.com https://discord.com 'self'"
"script-src": "https://*.posthog.com 'self'",
"frame-src": "https://www.youtube.com https://www.youtube-nocookie.com https://discord.com 'self'"
}
}
}
Expand Down
8 changes: 7 additions & 1 deletion apps/frontend/src/composables/auth.js
Original file line number Diff line number Diff line change
Expand Up @@ -111,7 +111,13 @@ export const getAuthUrl = (provider, redirect = "") => {
if (redirect === "") {
redirect = route.path;
}
const fullURL = `${config.public.siteUrl}${redirect}`;

let fullURL;
if (route.query.launcher) {
fullURL = `https://launcher-files.modrinth.com`;
} else {
fullURL = `${config.public.siteUrl}${redirect}`;
}

return `${config.public.apiBaseUrl}auth/init?provider=${provider}&url=${fullURL}`;
};
Expand Down
1 change: 1 addition & 0 deletions apps/frontend/src/layouts/empty.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
<template><slot id="main" /></template>
5 changes: 5 additions & 0 deletions apps/frontend/src/middleware/launcher-auth.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
export default defineNuxtRouteMiddleware((to) => {
if (to.query.launcher) {
setPageLayout("empty");
}
});
5 changes: 5 additions & 0 deletions apps/frontend/src/pages/auth.vue
Original file line number Diff line number Diff line change
@@ -1,3 +1,8 @@
<script setup lang="ts">
definePageMeta({
middleware: ["launcher-auth"],
});
</script>
<template>
<NuxtPage class="auth-container universal-card" />
</template>
Expand Down
25 changes: 19 additions & 6 deletions apps/frontend/src/pages/auth/sign-in.vue
Original file line number Diff line number Diff line change
Expand Up @@ -94,12 +94,24 @@
<div class="auth-form__additional-options">
<IntlFormatted :message-id="messages.additionalOptionsLabel">
<template #forgot-password-link="{ children }">
<NuxtLink class="text-link" to="/auth/reset-password">
<NuxtLink
class="text-link"
:to="{
path: '/auth/reset-password',
query: route.query,
}"
>
<component :is="() => children" />
</NuxtLink>
</template>
<template #create-account-link="{ children }">
<NuxtLink class="text-link" :to="signUpLink">
<NuxtLink
class="text-link"
:to="{
path: '/auth/sign-up',
query: route.query,
}"
>
<component :is="() => children" />
</NuxtLink>
</template>
Expand Down Expand Up @@ -193,10 +205,6 @@ const token = ref("");

const flow = ref(route.query.flow);

const signUpLink = computed(
() => `/auth/sign-up${route.query.redirect ? `?redirect=${route.query.redirect}` : ""}`,
);

async function beginPasswordSignIn() {
startLoading();
try {
Expand Down Expand Up @@ -252,6 +260,11 @@ async function begin2FASignIn() {
}

async function finishSignIn(token) {
if (route.query.launcher) {
await navigateTo(`https://launcher-files.modrinth.com/?code=${token}`, { external: true });
return;
}

if (token) {
await useAuth(token);
await useUser();
Expand Down
Loading
Loading