diff --git a/api/.sqlx/query-050b47e8c4f5300bdb04ae9f42a1897f68b0462ad93a29ce20bb652bbbb83420.json b/api/.sqlx/query-050b47e8c4f5300bdb04ae9f42a1897f68b0462ad93a29ce20bb652bbbb83420.json deleted file mode 100644 index b9c4edadc..000000000 --- a/api/.sqlx/query-050b47e8c4f5300bdb04ae9f42a1897f68b0462ad93a29ce20bb652bbbb83420.json +++ /dev/null @@ -1,99 +0,0 @@ -{ - "db_name": "PostgreSQL", - "query": "INSERT INTO users (name, email, avatar_url, github_id, is_blocked, is_staff)\n VALUES ($1, $2, $3, $4, $5, $6)\n RETURNING id, name, email, avatar_url, updated_at, created_at, github_id, is_blocked, is_staff, scope_limit,\n (SELECT COUNT(created_at) FROM scope_invites WHERE target_user_id = id) as \"invite_count!\",\n (SELECT COUNT(created_at) FROM scopes WHERE creator = id) as \"scope_usage!\",\n (CASE WHEN users.is_staff THEN (\n SELECT count(tickets.created_at) FROM tickets WHERE closed = false AND EXISTS (\n SELECT 1 FROM ticket_messages as tm WHERE tm.ticket_id = tickets.id AND tm.author = tickets.creator AND tm.created_at = (\n SELECT MAX(ticket_messages.created_at) FROM ticket_messages WHERE ticket_messages.ticket_id = tickets.id\n )\n )\n ) ELSE (\n SELECT COUNT(created_at) FROM tickets WHERE closed = false AND tickets.creator = users.id AND EXISTS (\n SELECT 1 FROM ticket_messages as tm WHERE tm.ticket_id = tickets.id AND tm.author != users.id AND tm.created_at > (\n SELECT MAX(tm2.created_at) FROM ticket_messages as tm2 WHERE tm2.ticket_id = tm.ticket_id AND tm2.author = users.id\n )\n )\n ) END) as \"newer_ticket_messages_count!\"\n ", - "describe": { - "columns": [ - { - "ordinal": 0, - "name": "id", - "type_info": "Uuid" - }, - { - "ordinal": 1, - "name": "name", - "type_info": "Text" - }, - { - "ordinal": 2, - "name": "email", - "type_info": "Varchar" - }, - { - "ordinal": 3, - "name": "avatar_url", - "type_info": "Text" - }, - { - "ordinal": 4, - "name": "updated_at", - "type_info": "Timestamptz" - }, - { - "ordinal": 5, - "name": "created_at", - "type_info": "Timestamptz" - }, - { - "ordinal": 6, - "name": "github_id", - "type_info": "Int8" - }, - { - "ordinal": 7, - "name": "is_blocked", - "type_info": "Bool" - }, - { - "ordinal": 8, - "name": "is_staff", - "type_info": "Bool" - }, - { - "ordinal": 9, - "name": "scope_limit", - "type_info": "Int4" - }, - { - "ordinal": 10, - "name": "invite_count!", - "type_info": "Int8" - }, - { - "ordinal": 11, - "name": "scope_usage!", - "type_info": "Int8" - }, - { - "ordinal": 12, - "name": "newer_ticket_messages_count!", - "type_info": "Int8" - } - ], - "parameters": { - "Left": [ - "Text", - "Varchar", - "Text", - "Int8", - "Bool", - "Bool" - ] - }, - "nullable": [ - false, - false, - true, - false, - false, - false, - true, - false, - false, - false, - null, - null, - null - ] - }, - "hash": "050b47e8c4f5300bdb04ae9f42a1897f68b0462ad93a29ce20bb652bbbb83420" -} diff --git a/api/.sqlx/query-ef0155c2926ea69baf0738c6317064adee44c3627443478d3a94a45b1748db25.json b/api/.sqlx/query-09064d0df28c61389f2ccff0d4f1ffa51b28dfa6f769f8770a01eafe0201ab46.json similarity index 67% rename from api/.sqlx/query-ef0155c2926ea69baf0738c6317064adee44c3627443478d3a94a45b1748db25.json rename to api/.sqlx/query-09064d0df28c61389f2ccff0d4f1ffa51b28dfa6f769f8770a01eafe0201ab46.json index 8a3f0cab6..da7b0bab1 100644 --- a/api/.sqlx/query-ef0155c2926ea69baf0738c6317064adee44c3627443478d3a94a45b1748db25.json +++ b/api/.sqlx/query-09064d0df28c61389f2ccff0d4f1ffa51b28dfa6f769f8770a01eafe0201ab46.json @@ -1,6 +1,6 @@ { "db_name": "PostgreSQL", - "query": "SELECT packages.scope \"package_scope: ScopeName\", packages.name \"package_name: PackageName\", packages.description \"package_description\", packages.github_repository_id \"package_github_repository_id\", packages.runtime_compat as \"package_runtime_compat: RuntimeCompat\", packages.readme_source as \"package_readme_source: ReadmeSource\", packages.when_featured \"package_when_featured\", packages.is_archived \"package_is_archived\", packages.updated_at \"package_updated_at\", packages.created_at \"package_created_at\",\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = packages.scope AND name = packages.name) as \"package_version_count!\",\n (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_latest_version\",\n (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_version_meta: PackageVersionMeta\",\n github_repositories.id \"github_repository_id?\", github_repositories.owner \"github_repository_owner?\", github_repositories.name \"github_repository_name?\", github_repositories.updated_at \"github_repository_updated_at?\", github_repositories.created_at \"github_repository_created_at?\"\n FROM packages\n LEFT JOIN github_repositories ON packages.github_repository_id = github_repositories.id\n WHERE (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND is_yanked = false AND version IS NOT NULL ORDER BY version DESC LIMIT 1) IS NOT NULL AND NOT packages.is_archived\n ORDER BY packages.created_at DESC\n LIMIT 10", + "query": "SELECT packages.scope \"package_scope: ScopeName\", packages.name \"package_name: PackageName\", packages.description \"package_description\", packages.github_repository_id \"package_github_repository_id\", packages.runtime_compat as \"package_runtime_compat: RuntimeCompat\", packages.readme_source as \"package_readme_source: ReadmeSource\", packages.when_featured \"package_when_featured\", packages.is_archived \"package_is_archived\", packages.is_private \"package_is_private\", packages.updated_at \"package_updated_at\", packages.created_at \"package_created_at\",\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = packages.scope AND name = packages.name) as \"package_version_count!\",\n (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_latest_version\",\n (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_version_meta: PackageVersionMeta\",\n github_repositories.id \"github_repository_id?\", github_repositories.owner \"github_repository_owner?\", github_repositories.name \"github_repository_name?\", github_repositories.updated_at \"github_repository_updated_at?\", github_repositories.created_at \"github_repository_created_at?\"\n FROM packages\n LEFT JOIN github_repositories ON packages.github_repository_id = github_repositories.id\n WHERE packages.when_featured IS NOT NULL AND NOT packages.is_archived AND NOT packages.is_private\n ORDER BY packages.when_featured DESC\n LIMIT 10", "describe": { "columns": [ { @@ -55,51 +55,56 @@ }, { "ordinal": 8, + "name": "package_is_private", + "type_info": "Bool" + }, + { + "ordinal": 9, "name": "package_updated_at", "type_info": "Timestamptz" }, { - "ordinal": 9, + "ordinal": 10, "name": "package_created_at", "type_info": "Timestamptz" }, { - "ordinal": 10, + "ordinal": 11, "name": "package_version_count!", "type_info": "Int8" }, { - "ordinal": 11, + "ordinal": 12, "name": "package_latest_version", "type_info": "Text" }, { - "ordinal": 12, + "ordinal": 13, "name": "package_version_meta: PackageVersionMeta", "type_info": "Jsonb" }, { - "ordinal": 13, + "ordinal": 14, "name": "github_repository_id?", "type_info": "Int8" }, { - "ordinal": 14, + "ordinal": 15, "name": "github_repository_owner?", "type_info": "Text" }, { - "ordinal": 15, + "ordinal": 16, "name": "github_repository_name?", "type_info": "Text" }, { - "ordinal": 16, + "ordinal": 17, "name": "github_repository_updated_at?", "type_info": "Timestamptz" }, { - "ordinal": 17, + "ordinal": 18, "name": "github_repository_created_at?", "type_info": "Timestamptz" } @@ -118,6 +123,7 @@ false, false, false, + false, null, null, null, @@ -128,5 +134,5 @@ false ] }, - "hash": "ef0155c2926ea69baf0738c6317064adee44c3627443478d3a94a45b1748db25" + "hash": "09064d0df28c61389f2ccff0d4f1ffa51b28dfa6f769f8770a01eafe0201ab46" } diff --git a/api/.sqlx/query-42bc09915e14ee2d075d95dff11eb31d3b1392ea9ad74e4be0865cb8fce402be.json b/api/.sqlx/query-0a80e3888c3dce8a884e9d6cdf113e39551d1c976d53eba93a4b58eeb97960ee.json similarity index 81% rename from api/.sqlx/query-42bc09915e14ee2d075d95dff11eb31d3b1392ea9ad74e4be0865cb8fce402be.json rename to api/.sqlx/query-0a80e3888c3dce8a884e9d6cdf113e39551d1c976d53eba93a4b58eeb97960ee.json index 16788c860..6d4cd7a09 100644 --- a/api/.sqlx/query-42bc09915e14ee2d075d95dff11eb31d3b1392ea9ad74e4be0865cb8fce402be.json +++ b/api/.sqlx/query-0a80e3888c3dce8a884e9d6cdf113e39551d1c976d53eba93a4b58eeb97960ee.json @@ -1,6 +1,6 @@ { "db_name": "PostgreSQL", - "query": "UPDATE packages\n SET is_archived = $3\n WHERE scope = $1 AND name = $2\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as \"latest_version\"", + "query": "UPDATE packages\n SET is_archived = $3\n WHERE scope = $1 AND name = $2\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, is_private, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as \"latest_version\"", "describe": { "columns": [ { @@ -55,21 +55,26 @@ }, { "ordinal": 8, + "name": "is_private", + "type_info": "Bool" + }, + { + "ordinal": 9, "name": "updated_at", "type_info": "Timestamptz" }, { - "ordinal": 9, + "ordinal": 10, "name": "created_at", "type_info": "Timestamptz" }, { - "ordinal": 10, + "ordinal": 11, "name": "version_count!", "type_info": "Int8" }, { - "ordinal": 11, + "ordinal": 12, "name": "latest_version", "type_info": "Text" } @@ -92,9 +97,10 @@ false, false, false, + false, null, null ] }, - "hash": "42bc09915e14ee2d075d95dff11eb31d3b1392ea9ad74e4be0865cb8fce402be" + "hash": "0a80e3888c3dce8a884e9d6cdf113e39551d1c976d53eba93a4b58eeb97960ee" } diff --git a/api/.sqlx/query-0ddb2cf66ee7e7d2c7341713b39b8dfe51e9edc309c346baaea94470cace57af.json b/api/.sqlx/query-0ddb2cf66ee7e7d2c7341713b39b8dfe51e9edc309c346baaea94470cace57af.json deleted file mode 100644 index 902544274..000000000 --- a/api/.sqlx/query-0ddb2cf66ee7e7d2c7341713b39b8dfe51e9edc309c346baaea94470cace57af.json +++ /dev/null @@ -1,76 +0,0 @@ -{ - "db_name": "PostgreSQL", - "query": "SELECT\n scope as \"scope: ScopeName\",\n description as \"description: ScopeDescription\",\n creator,\n package_limit,\n new_package_per_week_limit,\n publish_attempts_per_week_limit,\n verify_oidc_actor,\n require_publishing_from_ci,\n updated_at,\n created_at\n FROM scopes WHERE creator = $1\n ORDER BY scope ASC", - "describe": { - "columns": [ - { - "ordinal": 0, - "name": "scope: ScopeName", - "type_info": "Text" - }, - { - "ordinal": 1, - "name": "description: ScopeDescription", - "type_info": "Text" - }, - { - "ordinal": 2, - "name": "creator", - "type_info": "Uuid" - }, - { - "ordinal": 3, - "name": "package_limit", - "type_info": "Int4" - }, - { - "ordinal": 4, - "name": "new_package_per_week_limit", - "type_info": "Int4" - }, - { - "ordinal": 5, - "name": "publish_attempts_per_week_limit", - "type_info": "Int4" - }, - { - "ordinal": 6, - "name": "verify_oidc_actor", - "type_info": "Bool" - }, - { - "ordinal": 7, - "name": "require_publishing_from_ci", - "type_info": "Bool" - }, - { - "ordinal": 8, - "name": "updated_at", - "type_info": "Timestamptz" - }, - { - "ordinal": 9, - "name": "created_at", - "type_info": "Timestamptz" - } - ], - "parameters": { - "Left": [ - "Uuid" - ] - }, - "nullable": [ - false, - false, - false, - false, - false, - false, - false, - false, - false, - false - ] - }, - "hash": "0ddb2cf66ee7e7d2c7341713b39b8dfe51e9edc309c346baaea94470cace57af" -} diff --git a/api/.sqlx/query-0e8e4c876ea49c287f77dc33a1dd6c41dc7080e695249ff4a5a415df05139ece.json b/api/.sqlx/query-0e8e4c876ea49c287f77dc33a1dd6c41dc7080e695249ff4a5a415df05139ece.json deleted file mode 100644 index de37c9f85..000000000 --- a/api/.sqlx/query-0e8e4c876ea49c287f77dc33a1dd6c41dc7080e695249ff4a5a415df05139ece.json +++ /dev/null @@ -1,94 +0,0 @@ -{ - "db_name": "PostgreSQL", - "query": "DELETE FROM users\n WHERE id = $1\n RETURNING id, name, email, avatar_url, updated_at, created_at, github_id, is_blocked, is_staff, scope_limit,\n (SELECT COUNT(created_at) FROM scope_invites WHERE target_user_id = id) as \"invite_count!\",\n (SELECT COUNT(created_at) FROM scopes WHERE creator = id) as \"scope_usage!\",\n (CASE WHEN users.is_staff THEN (\n SELECT count(tickets.created_at) FROM tickets WHERE closed = false AND EXISTS (\n SELECT 1 FROM ticket_messages as tm WHERE tm.ticket_id = tickets.id AND tm.author = tickets.creator AND tm.created_at = (\n SELECT MAX(ticket_messages.created_at) FROM ticket_messages WHERE ticket_messages.ticket_id = tickets.id\n )\n )\n ) ELSE (\n SELECT COUNT(created_at) FROM tickets WHERE closed = false AND tickets.creator = users.id AND EXISTS (\n SELECT 1 FROM ticket_messages as tm WHERE tm.ticket_id = tickets.id AND tm.author != users.id AND tm.created_at > (\n SELECT MAX(tm2.created_at) FROM ticket_messages as tm2 WHERE tm2.ticket_id = tm.ticket_id AND tm2.author = users.id\n )\n )\n ) END) as \"newer_ticket_messages_count!\"\n ", - "describe": { - "columns": [ - { - "ordinal": 0, - "name": "id", - "type_info": "Uuid" - }, - { - "ordinal": 1, - "name": "name", - "type_info": "Text" - }, - { - "ordinal": 2, - "name": "email", - "type_info": "Varchar" - }, - { - "ordinal": 3, - "name": "avatar_url", - "type_info": "Text" - }, - { - "ordinal": 4, - "name": "updated_at", - "type_info": "Timestamptz" - }, - { - "ordinal": 5, - "name": "created_at", - "type_info": "Timestamptz" - }, - { - "ordinal": 6, - "name": "github_id", - "type_info": "Int8" - }, - { - "ordinal": 7, - "name": "is_blocked", - "type_info": "Bool" - }, - { - "ordinal": 8, - "name": "is_staff", - "type_info": "Bool" - }, - { - "ordinal": 9, - "name": "scope_limit", - "type_info": "Int4" - }, - { - "ordinal": 10, - "name": "invite_count!", - "type_info": "Int8" - }, - { - "ordinal": 11, - "name": "scope_usage!", - "type_info": "Int8" - }, - { - "ordinal": 12, - "name": "newer_ticket_messages_count!", - "type_info": "Int8" - } - ], - "parameters": { - "Left": [ - "Uuid" - ] - }, - "nullable": [ - false, - false, - true, - false, - false, - false, - true, - false, - false, - false, - null, - null, - null - ] - }, - "hash": "0e8e4c876ea49c287f77dc33a1dd6c41dc7080e695249ff4a5a415df05139ece" -} diff --git a/api/.sqlx/query-b43a8cac5abc471e9e2781341c713f8b4c8c7c1b32d28b911b7449ab69ba43fc.json b/api/.sqlx/query-22c8d5698ea739ca61c701a75407573898e37b485055291aac01ff65591ca5c0.json similarity index 82% rename from api/.sqlx/query-b43a8cac5abc471e9e2781341c713f8b4c8c7c1b32d28b911b7449ab69ba43fc.json rename to api/.sqlx/query-22c8d5698ea739ca61c701a75407573898e37b485055291aac01ff65591ca5c0.json index 9400e2fb9..926bd3e98 100644 --- a/api/.sqlx/query-b43a8cac5abc471e9e2781341c713f8b4c8c7c1b32d28b911b7449ab69ba43fc.json +++ b/api/.sqlx/query-22c8d5698ea739ca61c701a75407573898e37b485055291aac01ff65591ca5c0.json @@ -1,6 +1,6 @@ { "db_name": "PostgreSQL", - "query": "UPDATE packages\n SET readme_source = $3\n WHERE scope = $1 AND name = $2\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as \"latest_version\"", + "query": "UPDATE packages\n SET readme_source = $3\n WHERE scope = $1 AND name = $2\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, is_private, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as \"latest_version\"", "describe": { "columns": [ { @@ -55,21 +55,26 @@ }, { "ordinal": 8, + "name": "is_private", + "type_info": "Bool" + }, + { + "ordinal": 9, "name": "updated_at", "type_info": "Timestamptz" }, { - "ordinal": 9, + "ordinal": 10, "name": "created_at", "type_info": "Timestamptz" }, { - "ordinal": 10, + "ordinal": 11, "name": "version_count!", "type_info": "Int8" }, { - "ordinal": 11, + "ordinal": 12, "name": "latest_version", "type_info": "Text" } @@ -102,9 +107,10 @@ false, false, false, + false, null, null ] }, - "hash": "b43a8cac5abc471e9e2781341c713f8b4c8c7c1b32d28b911b7449ab69ba43fc" + "hash": "22c8d5698ea739ca61c701a75407573898e37b485055291aac01ff65591ca5c0" } diff --git a/api/.sqlx/query-785dbd6f774c40c14f8a8b748e7a5287e7f555ee1d1feae9dabab8642daffa9b.json b/api/.sqlx/query-2b46ea4eb5a53a21fbbbbc0da441cb90a993091dcd8feb45f26dfaa86a441e6c.json similarity index 75% rename from api/.sqlx/query-785dbd6f774c40c14f8a8b748e7a5287e7f555ee1d1feae9dabab8642daffa9b.json rename to api/.sqlx/query-2b46ea4eb5a53a21fbbbbc0da441cb90a993091dcd8feb45f26dfaa86a441e6c.json index 022ccb4c4..e902bb421 100644 --- a/api/.sqlx/query-785dbd6f774c40c14f8a8b748e7a5287e7f555ee1d1feae9dabab8642daffa9b.json +++ b/api/.sqlx/query-2b46ea4eb5a53a21fbbbbc0da441cb90a993091dcd8feb45f26dfaa86a441e6c.json @@ -1,6 +1,6 @@ { "db_name": "PostgreSQL", - "query": "UPDATE packages\n SET description = $3\n WHERE scope = $1 AND name = $2\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as \"latest_version\",\n (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_version_meta: PackageVersionMeta\"", + "query": "UPDATE packages\n SET description = $3\n WHERE scope = $1 AND name = $2\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, is_private, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as \"latest_version\",\n (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_version_meta: PackageVersionMeta\"", "describe": { "columns": [ { @@ -55,26 +55,31 @@ }, { "ordinal": 8, + "name": "is_private", + "type_info": "Bool" + }, + { + "ordinal": 9, "name": "updated_at", "type_info": "Timestamptz" }, { - "ordinal": 9, + "ordinal": 10, "name": "created_at", "type_info": "Timestamptz" }, { - "ordinal": 10, + "ordinal": 11, "name": "version_count!", "type_info": "Int8" }, { - "ordinal": 11, + "ordinal": 12, "name": "latest_version", "type_info": "Text" }, { - "ordinal": 12, + "ordinal": 13, "name": "package_version_meta: PackageVersionMeta", "type_info": "Jsonb" } @@ -97,10 +102,11 @@ false, false, false, + false, null, null, null ] }, - "hash": "785dbd6f774c40c14f8a8b748e7a5287e7f555ee1d1feae9dabab8642daffa9b" + "hash": "2b46ea4eb5a53a21fbbbbc0da441cb90a993091dcd8feb45f26dfaa86a441e6c" } diff --git a/api/.sqlx/query-30441825bf3627e9fd7b99368f0b185da1afcd31f3e2762329dd2cbf0fd3c610.json b/api/.sqlx/query-30441825bf3627e9fd7b99368f0b185da1afcd31f3e2762329dd2cbf0fd3c610.json deleted file mode 100644 index b050db161..000000000 --- a/api/.sqlx/query-30441825bf3627e9fd7b99368f0b185da1afcd31f3e2762329dd2cbf0fd3c610.json +++ /dev/null @@ -1,107 +0,0 @@ -{ - "db_name": "PostgreSQL", - "query": "INSERT INTO package_versions (scope, name, version, user_id, readme_path, exports, uses_npm, meta)\n VALUES ($1, $2, $3, $4, $5, $6, $7, $8)\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", version as \"version: Version\", user_id, readme_path as \"readme_path: PackagePath\", exports as \"exports: ExportsMap\", is_yanked, uses_npm, meta as \"meta: PackageVersionMeta\", updated_at, created_at, rekor_log_id,\n (SELECT COUNT(*)\n FROM package_versions AS pv\n WHERE pv.scope = package_versions.scope\n AND pv.name = package_versions.name\n AND pv.version > package_versions.version\n AND pv.version NOT LIKE '%-%'\n AND pv.is_yanked = false) as \"newer_versions_count!\",\n (SELECT COALESCE(SUM(dl.count), 0)\n FROM version_download_counts_24h as dl\n WHERE dl.scope = package_versions.scope\n AND dl.package = package_versions.name\n AND dl.version = package_versions.version) as \"lifetime_download_count!\"", - "describe": { - "columns": [ - { - "ordinal": 0, - "name": "scope: ScopeName", - "type_info": "Text" - }, - { - "ordinal": 1, - "name": "name: PackageName", - "type_info": "Text" - }, - { - "ordinal": 2, - "name": "version: Version", - "type_info": "Text" - }, - { - "ordinal": 3, - "name": "user_id", - "type_info": "Uuid" - }, - { - "ordinal": 4, - "name": "readme_path: PackagePath", - "type_info": "Text" - }, - { - "ordinal": 5, - "name": "exports: ExportsMap", - "type_info": "Jsonb" - }, - { - "ordinal": 6, - "name": "is_yanked", - "type_info": "Bool" - }, - { - "ordinal": 7, - "name": "uses_npm", - "type_info": "Bool" - }, - { - "ordinal": 8, - "name": "meta: PackageVersionMeta", - "type_info": "Jsonb" - }, - { - "ordinal": 9, - "name": "updated_at", - "type_info": "Timestamptz" - }, - { - "ordinal": 10, - "name": "created_at", - "type_info": "Timestamptz" - }, - { - "ordinal": 11, - "name": "rekor_log_id", - "type_info": "Text" - }, - { - "ordinal": 12, - "name": "newer_versions_count!", - "type_info": "Int8" - }, - { - "ordinal": 13, - "name": "lifetime_download_count!", - "type_info": "Int8" - } - ], - "parameters": { - "Left": [ - "Text", - "Text", - "Text", - "Uuid", - "Text", - "Jsonb", - "Bool", - "Jsonb" - ] - }, - "nullable": [ - false, - false, - false, - true, - true, - false, - false, - false, - false, - false, - false, - true, - null, - null - ] - }, - "hash": "30441825bf3627e9fd7b99368f0b185da1afcd31f3e2762329dd2cbf0fd3c610" -} diff --git a/api/.sqlx/query-7565c8ea2ffa802ba5b6d17816887f4f65868ed519aa8ad006dd7cf2124a63bd.json b/api/.sqlx/query-3302ed990a043926109579e49b19077b8dd5628fadebd5ab936a55ef038786ca.json similarity index 73% rename from api/.sqlx/query-7565c8ea2ffa802ba5b6d17816887f4f65868ed519aa8ad006dd7cf2124a63bd.json rename to api/.sqlx/query-3302ed990a043926109579e49b19077b8dd5628fadebd5ab936a55ef038786ca.json index 4c2e72d41..f60a77630 100644 --- a/api/.sqlx/query-7565c8ea2ffa802ba5b6d17816887f4f65868ed519aa8ad006dd7cf2124a63bd.json +++ b/api/.sqlx/query-3302ed990a043926109579e49b19077b8dd5628fadebd5ab936a55ef038786ca.json @@ -1,6 +1,6 @@ { "db_name": "PostgreSQL", - "query": "UPDATE packages\n SET github_repository_id = $3\n WHERE scope = $1 AND name = $2\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"latest_version\",\n (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_version_meta: PackageVersionMeta\"", + "query": "UPDATE packages\n SET github_repository_id = $3\n WHERE scope = $1 AND name = $2\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, is_private, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"latest_version\",\n (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_version_meta: PackageVersionMeta\"", "describe": { "columns": [ { @@ -55,26 +55,31 @@ }, { "ordinal": 8, + "name": "is_private", + "type_info": "Bool" + }, + { + "ordinal": 9, "name": "updated_at", "type_info": "Timestamptz" }, { - "ordinal": 9, + "ordinal": 10, "name": "created_at", "type_info": "Timestamptz" }, { - "ordinal": 10, + "ordinal": 11, "name": "version_count!", "type_info": "Int8" }, { - "ordinal": 11, + "ordinal": 12, "name": "latest_version", "type_info": "Text" }, { - "ordinal": 12, + "ordinal": 13, "name": "package_version_meta: PackageVersionMeta", "type_info": "Jsonb" } @@ -97,10 +102,11 @@ false, false, false, + false, null, null, null ] }, - "hash": "7565c8ea2ffa802ba5b6d17816887f4f65868ed519aa8ad006dd7cf2124a63bd" + "hash": "3302ed990a043926109579e49b19077b8dd5628fadebd5ab936a55ef038786ca" } diff --git a/api/.sqlx/query-35632bc48d97695339900965cf98b93a12da06bb610173c1e39f9997f97e9610.json b/api/.sqlx/query-35632bc48d97695339900965cf98b93a12da06bb610173c1e39f9997f97e9610.json deleted file mode 100644 index 8dd84463c..000000000 --- a/api/.sqlx/query-35632bc48d97695339900965cf98b93a12da06bb610173c1e39f9997f97e9610.json +++ /dev/null @@ -1,48 +0,0 @@ -{ - "db_name": "PostgreSQL", - "query": "\n SELECT time_bucket, kind as \"kind: DownloadKind\", count\n FROM version_download_counts_4h\n WHERE scope = $1 AND package = $2 AND version = $3 AND time_bucket >= $4 AND time_bucket < $5\n ORDER BY time_bucket ASC\n ", - "describe": { - "columns": [ - { - "ordinal": 0, - "name": "time_bucket", - "type_info": "Timestamptz" - }, - { - "ordinal": 1, - "name": "kind: DownloadKind", - "type_info": { - "Custom": { - "name": "download_kind", - "kind": { - "Enum": [ - "npm_tgz", - "jsr_meta" - ] - } - } - } - }, - { - "ordinal": 2, - "name": "count", - "type_info": "Int4" - } - ], - "parameters": { - "Left": [ - "Text", - "Text", - "Text", - "Timestamptz", - "Timestamptz" - ] - }, - "nullable": [ - false, - false, - false - ] - }, - "hash": "35632bc48d97695339900965cf98b93a12da06bb610173c1e39f9997f97e9610" -} diff --git a/api/.sqlx/query-3f118b22cfc900a7f6e3e483f97e9761bc495a34441ddf2a128fec6364be6a62.json b/api/.sqlx/query-3f118b22cfc900a7f6e3e483f97e9761bc495a34441ddf2a128fec6364be6a62.json deleted file mode 100644 index e019b4269..000000000 --- a/api/.sqlx/query-3f118b22cfc900a7f6e3e483f97e9761bc495a34441ddf2a128fec6364be6a62.json +++ /dev/null @@ -1,48 +0,0 @@ -{ - "db_name": "PostgreSQL", - "query": "INSERT INTO scope_members (scope, user_id, is_admin)\n VALUES ($1, $2, $3)\n RETURNING scope as \"scope: ScopeName\", user_id, is_admin, updated_at, created_at", - "describe": { - "columns": [ - { - "ordinal": 0, - "name": "scope: ScopeName", - "type_info": "Text" - }, - { - "ordinal": 1, - "name": "user_id", - "type_info": "Uuid" - }, - { - "ordinal": 2, - "name": "is_admin", - "type_info": "Bool" - }, - { - "ordinal": 3, - "name": "updated_at", - "type_info": "Timestamptz" - }, - { - "ordinal": 4, - "name": "created_at", - "type_info": "Timestamptz" - } - ], - "parameters": { - "Left": [ - "Text", - "Uuid", - "Bool" - ] - }, - "nullable": [ - false, - false, - false, - false, - false - ] - }, - "hash": "3f118b22cfc900a7f6e3e483f97e9761bc495a34441ddf2a128fec6364be6a62" -} diff --git a/api/.sqlx/query-51fd48d86ae305c6fc527fd5b062a35c41672736f94acea3afe9ad369b9f53b5.json b/api/.sqlx/query-51fd48d86ae305c6fc527fd5b062a35c41672736f94acea3afe9ad369b9f53b5.json deleted file mode 100644 index bd69526a4..000000000 --- a/api/.sqlx/query-51fd48d86ae305c6fc527fd5b062a35c41672736f94acea3afe9ad369b9f53b5.json +++ /dev/null @@ -1,69 +0,0 @@ -{ - "db_name": "PostgreSQL", - "query": "INSERT INTO package_files (scope, name, version, path, size, checksum)\n VALUES ($1, $2, $3, $4, $5, $6)\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", version as \"version: Version\", path as \"path: PackagePath\", size, checksum, updated_at, created_at", - "describe": { - "columns": [ - { - "ordinal": 0, - "name": "scope: ScopeName", - "type_info": "Text" - }, - { - "ordinal": 1, - "name": "name: PackageName", - "type_info": "Text" - }, - { - "ordinal": 2, - "name": "version: Version", - "type_info": "Text" - }, - { - "ordinal": 3, - "name": "path: PackagePath", - "type_info": "Text" - }, - { - "ordinal": 4, - "name": "size", - "type_info": "Int4" - }, - { - "ordinal": 5, - "name": "checksum", - "type_info": "Text" - }, - { - "ordinal": 6, - "name": "updated_at", - "type_info": "Timestamptz" - }, - { - "ordinal": 7, - "name": "created_at", - "type_info": "Timestamptz" - } - ], - "parameters": { - "Left": [ - "Text", - "Text", - "Text", - "Text", - "Int4", - "Text" - ] - }, - "nullable": [ - false, - false, - false, - false, - false, - true, - false, - false - ] - }, - "hash": "51fd48d86ae305c6fc527fd5b062a35c41672736f94acea3afe9ad369b9f53b5" -} diff --git a/api/.sqlx/query-0824a1acff26ba7c43687f2c3305e9a0824a01e40c708b246881d0faa429e51d.json b/api/.sqlx/query-5c25db7b857ff64e0004ae6122a0f5c2e4067899bdc4e83b61976defce4ab98d.json similarity index 64% rename from api/.sqlx/query-0824a1acff26ba7c43687f2c3305e9a0824a01e40c708b246881d0faa429e51d.json rename to api/.sqlx/query-5c25db7b857ff64e0004ae6122a0f5c2e4067899bdc4e83b61976defce4ab98d.json index 8631733f9..e8b87b0e1 100644 --- a/api/.sqlx/query-0824a1acff26ba7c43687f2c3305e9a0824a01e40c708b246881d0faa429e51d.json +++ b/api/.sqlx/query-5c25db7b857ff64e0004ae6122a0f5c2e4067899bdc4e83b61976defce4ab98d.json @@ -1,6 +1,6 @@ { "db_name": "PostgreSQL", - "query": "SELECT COUNT(created_at) FROM packages WHERE scope = $1 AND ($2 = true OR packages.is_archived = false);", + "query": "SELECT COUNT(created_at) FROM packages WHERE scope = $1 AND ($2 = true OR packages.is_archived = false) AND ($3 = true OR packages.is_private = false);", "describe": { "columns": [ { @@ -12,6 +12,7 @@ "parameters": { "Left": [ "Text", + "Bool", "Bool" ] }, @@ -19,5 +20,5 @@ null ] }, - "hash": "0824a1acff26ba7c43687f2c3305e9a0824a01e40c708b246881d0faa429e51d" + "hash": "5c25db7b857ff64e0004ae6122a0f5c2e4067899bdc4e83b61976defce4ab98d" } diff --git a/api/.sqlx/query-ad4dad0f6bf1d42a787cbb3fbc0854131f1d2d293cbb4faa8f69ae7f91c8ecb9.json b/api/.sqlx/query-9a6acbec173320e7732884e30fc9d59d2a1acd00d8086ef42599cdd12e3196a1.json similarity index 65% rename from api/.sqlx/query-ad4dad0f6bf1d42a787cbb3fbc0854131f1d2d293cbb4faa8f69ae7f91c8ecb9.json rename to api/.sqlx/query-9a6acbec173320e7732884e30fc9d59d2a1acd00d8086ef42599cdd12e3196a1.json index 834d1032a..4b2838fdf 100644 --- a/api/.sqlx/query-ad4dad0f6bf1d42a787cbb3fbc0854131f1d2d293cbb4faa8f69ae7f91c8ecb9.json +++ b/api/.sqlx/query-9a6acbec173320e7732884e30fc9d59d2a1acd00d8086ef42599cdd12e3196a1.json @@ -1,6 +1,6 @@ { "db_name": "PostgreSQL", - "query": "SELECT packages.scope \"package_scope: ScopeName\", packages.name \"package_name: PackageName\", packages.description \"package_description\", packages.github_repository_id \"package_github_repository_id\", packages.runtime_compat as \"package_runtime_compat: RuntimeCompat\", packages.readme_source as \"package_readme_source: ReadmeSource\", packages.when_featured \"package_when_featured\", packages.is_archived \"package_is_archived\", packages.updated_at \"package_updated_at\", packages.created_at \"package_created_at\",\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = packages.scope AND name = packages.name) as \"package_version_count!\",\n (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_latest_version\",\n (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_version_meta: PackageVersionMeta\",\n github_repositories.id \"github_repository_id?\", github_repositories.owner \"github_repository_owner?\", github_repositories.name \"github_repository_name?\", github_repositories.updated_at \"github_repository_updated_at?\", github_repositories.created_at \"github_repository_created_at?\"\n FROM packages\n LEFT JOIN github_repositories ON packages.github_repository_id = github_repositories.id\n WHERE packages.when_featured IS NOT NULL AND NOT packages.is_archived\n ORDER BY packages.when_featured DESC\n LIMIT 10", + "query": "SELECT packages.scope \"package_scope: ScopeName\", packages.name \"package_name: PackageName\", packages.description \"package_description\", packages.github_repository_id \"package_github_repository_id\", packages.runtime_compat as \"package_runtime_compat: RuntimeCompat\", packages.readme_source as \"package_readme_source: ReadmeSource\", packages.when_featured \"package_when_featured\", packages.is_archived \"package_is_archived\", packages.is_private \"package_is_private\", packages.updated_at \"package_updated_at\", packages.created_at \"package_created_at\",\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = packages.scope AND name = packages.name) as \"package_version_count!\",\n (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_latest_version\",\n (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_version_meta: PackageVersionMeta\",\n github_repositories.id \"github_repository_id?\", github_repositories.owner \"github_repository_owner?\", github_repositories.name \"github_repository_name?\", github_repositories.updated_at \"github_repository_updated_at?\", github_repositories.created_at \"github_repository_created_at?\"\n FROM packages\n LEFT JOIN github_repositories ON packages.github_repository_id = github_repositories.id\n WHERE (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND is_yanked = false AND version IS NOT NULL ORDER BY version DESC LIMIT 1) IS NOT NULL AND NOT packages.is_archived AND NOT packages.is_private\n ORDER BY packages.created_at DESC\n LIMIT 10", "describe": { "columns": [ { @@ -55,51 +55,56 @@ }, { "ordinal": 8, + "name": "package_is_private", + "type_info": "Bool" + }, + { + "ordinal": 9, "name": "package_updated_at", "type_info": "Timestamptz" }, { - "ordinal": 9, + "ordinal": 10, "name": "package_created_at", "type_info": "Timestamptz" }, { - "ordinal": 10, + "ordinal": 11, "name": "package_version_count!", "type_info": "Int8" }, { - "ordinal": 11, + "ordinal": 12, "name": "package_latest_version", "type_info": "Text" }, { - "ordinal": 12, + "ordinal": 13, "name": "package_version_meta: PackageVersionMeta", "type_info": "Jsonb" }, { - "ordinal": 13, + "ordinal": 14, "name": "github_repository_id?", "type_info": "Int8" }, { - "ordinal": 14, + "ordinal": 15, "name": "github_repository_owner?", "type_info": "Text" }, { - "ordinal": 15, + "ordinal": 16, "name": "github_repository_name?", "type_info": "Text" }, { - "ordinal": 16, + "ordinal": 17, "name": "github_repository_updated_at?", "type_info": "Timestamptz" }, { - "ordinal": 17, + "ordinal": 18, "name": "github_repository_created_at?", "type_info": "Timestamptz" } @@ -118,6 +123,7 @@ false, false, false, + false, null, null, null, @@ -128,5 +134,5 @@ false ] }, - "hash": "ad4dad0f6bf1d42a787cbb3fbc0854131f1d2d293cbb4faa8f69ae7f91c8ecb9" + "hash": "9a6acbec173320e7732884e30fc9d59d2a1acd00d8086ef42599cdd12e3196a1" } diff --git a/api/.sqlx/query-a8050aebace5099be9493ab562f709cfe002530b6e0cfca2cdf1724da907d051.json b/api/.sqlx/query-a8050aebace5099be9493ab562f709cfe002530b6e0cfca2cdf1724da907d051.json new file mode 100644 index 000000000..6607c926e --- /dev/null +++ b/api/.sqlx/query-a8050aebace5099be9493ab562f709cfe002530b6e0cfca2cdf1724da907d051.json @@ -0,0 +1,106 @@ +{ + "db_name": "PostgreSQL", + "query": "UPDATE packages\n SET is_private = $3\n WHERE scope = $1 AND name = $2\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, is_private, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as \"latest_version\"", + "describe": { + "columns": [ + { + "ordinal": 0, + "name": "scope: ScopeName", + "type_info": "Text" + }, + { + "ordinal": 1, + "name": "name: PackageName", + "type_info": "Text" + }, + { + "ordinal": 2, + "name": "description", + "type_info": "Text" + }, + { + "ordinal": 3, + "name": "github_repository_id", + "type_info": "Int8" + }, + { + "ordinal": 4, + "name": "runtime_compat: RuntimeCompat", + "type_info": "Jsonb" + }, + { + "ordinal": 5, + "name": "readme_source: ReadmeSource", + "type_info": { + "Custom": { + "name": "package_readme_source", + "kind": { + "Enum": [ + "readme", + "jsdoc" + ] + } + } + } + }, + { + "ordinal": 6, + "name": "when_featured", + "type_info": "Timestamptz" + }, + { + "ordinal": 7, + "name": "is_archived", + "type_info": "Bool" + }, + { + "ordinal": 8, + "name": "is_private", + "type_info": "Bool" + }, + { + "ordinal": 9, + "name": "updated_at", + "type_info": "Timestamptz" + }, + { + "ordinal": 10, + "name": "created_at", + "type_info": "Timestamptz" + }, + { + "ordinal": 11, + "name": "version_count!", + "type_info": "Int8" + }, + { + "ordinal": 12, + "name": "latest_version", + "type_info": "Text" + } + ], + "parameters": { + "Left": [ + "Text", + "Text", + "Bool" + ] + }, + "nullable": [ + false, + false, + false, + true, + false, + false, + true, + false, + false, + false, + false, + null, + null + ] + }, + "hash": "a8050aebace5099be9493ab562f709cfe002530b6e0cfca2cdf1724da907d051" +} diff --git a/api/.sqlx/query-af37a947380c91b98ef36a7f2bcafabc2574dae3f240befb41e4fb4e74280528.json b/api/.sqlx/query-af37a947380c91b98ef36a7f2bcafabc2574dae3f240befb41e4fb4e74280528.json deleted file mode 100644 index c1da7eb2b..000000000 --- a/api/.sqlx/query-af37a947380c91b98ef36a7f2bcafabc2574dae3f240befb41e4fb4e74280528.json +++ /dev/null @@ -1,14 +0,0 @@ -{ - "db_name": "PostgreSQL", - "query": "INSERT INTO bad_words (word) VALUES ($1)", - "describe": { - "columns": [], - "parameters": { - "Left": [ - "Text" - ] - }, - "nullable": [] - }, - "hash": "af37a947380c91b98ef36a7f2bcafabc2574dae3f240befb41e4fb4e74280528" -} diff --git a/api/.sqlx/query-246465b7114a74de5f74426e402ff9f2d708119dd91b92100d441d338e3e7383.json b/api/.sqlx/query-b3a4a3c8d04a6a26c21054b9e104f19538e11c45b33414c29609729ed417bdb6.json similarity index 81% rename from api/.sqlx/query-246465b7114a74de5f74426e402ff9f2d708119dd91b92100d441d338e3e7383.json rename to api/.sqlx/query-b3a4a3c8d04a6a26c21054b9e104f19538e11c45b33414c29609729ed417bdb6.json index 1963d0356..09c4d6e41 100644 --- a/api/.sqlx/query-246465b7114a74de5f74426e402ff9f2d708119dd91b92100d441d338e3e7383.json +++ b/api/.sqlx/query-b3a4a3c8d04a6a26c21054b9e104f19538e11c45b33414c29609729ed417bdb6.json @@ -1,6 +1,6 @@ { "db_name": "PostgreSQL", - "query": "UPDATE packages\n SET when_featured = $3\n WHERE scope = $1 AND name = $2\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as \"latest_version\"", + "query": "UPDATE packages\n SET when_featured = $3\n WHERE scope = $1 AND name = $2\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, is_private, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as \"latest_version\"", "describe": { "columns": [ { @@ -55,21 +55,26 @@ }, { "ordinal": 8, + "name": "is_private", + "type_info": "Bool" + }, + { + "ordinal": 9, "name": "updated_at", "type_info": "Timestamptz" }, { - "ordinal": 9, + "ordinal": 10, "name": "created_at", "type_info": "Timestamptz" }, { - "ordinal": 10, + "ordinal": 11, "name": "version_count!", "type_info": "Int8" }, { - "ordinal": 11, + "ordinal": 12, "name": "latest_version", "type_info": "Text" } @@ -92,9 +97,10 @@ false, false, false, + false, null, null ] }, - "hash": "246465b7114a74de5f74426e402ff9f2d708119dd91b92100d441d338e3e7383" + "hash": "b3a4a3c8d04a6a26c21054b9e104f19538e11c45b33414c29609729ed417bdb6" } diff --git a/api/.sqlx/query-ae936fd4921cd295d2b577c20976f56a46a140f78eee41f4dadbddec40c8852b.json b/api/.sqlx/query-ba22535d224791f09049bb039d4596be21408a971c6c422f072c23ce3c64dfcf.json similarity index 93% rename from api/.sqlx/query-ae936fd4921cd295d2b577c20976f56a46a140f78eee41f4dadbddec40c8852b.json rename to api/.sqlx/query-ba22535d224791f09049bb039d4596be21408a971c6c422f072c23ce3c64dfcf.json index 3dccd63f7..92b186b63 100644 --- a/api/.sqlx/query-ae936fd4921cd295d2b577c20976f56a46a140f78eee41f4dadbddec40c8852b.json +++ b/api/.sqlx/query-ba22535d224791f09049bb039d4596be21408a971c6c422f072c23ce3c64dfcf.json @@ -1,6 +1,6 @@ { "db_name": "PostgreSQL", - "query": "SELECT package_versions.scope as \"scope: ScopeName\", package_versions.name as \"name: PackageName\", package_versions.version as \"version: Version\", package_versions.user_id, package_versions.readme_path as \"readme_path: PackagePath\", package_versions.exports as \"exports: ExportsMap\", package_versions.is_yanked, package_versions.uses_npm, package_versions.meta as \"meta: PackageVersionMeta\", package_versions.updated_at, package_versions.created_at, package_versions.rekor_log_id,\n (SELECT COUNT(*)\n FROM package_versions AS pv\n WHERE pv.scope = package_versions.scope\n AND pv.name = package_versions.name\n AND pv.version > package_versions.version\n AND pv.version NOT LIKE '%-%'\n AND pv.is_yanked = false) as \"newer_versions_count!\",\n (SELECT COALESCE(SUM(dl.count), 0)\n FROM version_download_counts_24h as dl\n WHERE dl.scope = package_versions.scope\n AND dl.package = package_versions.name\n AND dl.version = package_versions.version) as \"lifetime_download_count!\"\n FROM package_versions\n JOIN packages ON packages.scope = package_versions.scope AND packages.name = package_versions.name\n WHERE NOT packages.is_archived\n ORDER BY package_versions.created_at DESC\n LIMIT 10", + "query": "SELECT package_versions.scope as \"scope: ScopeName\", package_versions.name as \"name: PackageName\", package_versions.version as \"version: Version\", package_versions.user_id, package_versions.readme_path as \"readme_path: PackagePath\", package_versions.exports as \"exports: ExportsMap\", package_versions.is_yanked, package_versions.uses_npm, package_versions.meta as \"meta: PackageVersionMeta\", package_versions.updated_at, package_versions.created_at, package_versions.rekor_log_id,\n (SELECT COUNT(*)\n FROM package_versions AS pv\n WHERE pv.scope = package_versions.scope\n AND pv.name = package_versions.name\n AND pv.version > package_versions.version\n AND pv.version NOT LIKE '%-%'\n AND pv.is_yanked = false) as \"newer_versions_count!\",\n (SELECT COALESCE(SUM(dl.count), 0)\n FROM version_download_counts_24h as dl\n WHERE dl.scope = package_versions.scope\n AND dl.package = package_versions.name\n AND dl.version = package_versions.version) as \"lifetime_download_count!\"\n FROM package_versions\n JOIN packages ON packages.scope = package_versions.scope AND packages.name = package_versions.name\n WHERE NOT packages.is_archived AND NOT packages.is_private\n ORDER BY package_versions.created_at DESC\n LIMIT 10", "describe": { "columns": [ { @@ -94,5 +94,5 @@ null ] }, - "hash": "ae936fd4921cd295d2b577c20976f56a46a140f78eee41f4dadbddec40c8852b" + "hash": "ba22535d224791f09049bb039d4596be21408a971c6c422f072c23ce3c64dfcf" } diff --git a/api/.sqlx/query-ce694bc69d1154fa4bc5cc33f2b067f1c06831da03a15512f446c8f146bf120b.json b/api/.sqlx/query-bcd2d6abf8d3ff95b1dc96d68db1ea9f49cd312dcf6d4a891d9dbdb46d7ffbbc.json similarity index 66% rename from api/.sqlx/query-ce694bc69d1154fa4bc5cc33f2b067f1c06831da03a15512f446c8f146bf120b.json rename to api/.sqlx/query-bcd2d6abf8d3ff95b1dc96d68db1ea9f49cd312dcf6d4a891d9dbdb46d7ffbbc.json index d78d425ec..dc3138bb0 100644 --- a/api/.sqlx/query-ce694bc69d1154fa4bc5cc33f2b067f1c06831da03a15512f446c8f146bf120b.json +++ b/api/.sqlx/query-bcd2d6abf8d3ff95b1dc96d68db1ea9f49cd312dcf6d4a891d9dbdb46d7ffbbc.json @@ -1,6 +1,6 @@ { "db_name": "PostgreSQL", - "query": "SELECT packages.scope \"package_scope: ScopeName\", packages.name \"package_name: PackageName\", packages.description \"package_description\", packages.github_repository_id \"package_github_repository_id\", packages.runtime_compat as \"package_runtime_compat: RuntimeCompat\", packages.readme_source as \"package_readme_source: ReadmeSource\", packages.when_featured \"package_when_featured\", packages.is_archived \"package_is_archived\", packages.updated_at \"package_updated_at\", packages.created_at \"package_created_at\",\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = packages.scope AND name = packages.name) as \"package_version_count!\",\n (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_latest_version\",\n (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_version_meta: PackageVersionMeta\",\n github_repositories.id \"github_repository_id?\", github_repositories.owner \"github_repository_owner?\", github_repositories.name \"github_repository_name?\", github_repositories.updated_at \"github_repository_updated_at?\", github_repositories.created_at \"github_repository_created_at?\"\n FROM packages\n LEFT JOIN github_repositories ON packages.github_repository_id = github_repositories.id\n WHERE packages.scope = $1 AND ($2 = true OR packages.is_archived = false)\n ORDER BY packages.is_archived ASC, packages.name\n OFFSET $3 LIMIT $4", + "query": "SELECT packages.scope \"package_scope: ScopeName\", packages.name \"package_name: PackageName\", packages.description \"package_description\", packages.github_repository_id \"package_github_repository_id\", packages.runtime_compat as \"package_runtime_compat: RuntimeCompat\", packages.readme_source as \"package_readme_source: ReadmeSource\", packages.when_featured \"package_when_featured\", packages.is_archived \"package_is_archived\", packages.is_private \"package_is_private\", packages.updated_at \"package_updated_at\", packages.created_at \"package_created_at\",\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = packages.scope AND name = packages.name) as \"package_version_count!\",\n (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_latest_version\",\n (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_version_meta: PackageVersionMeta\",\n github_repositories.id \"github_repository_id?\", github_repositories.owner \"github_repository_owner?\", github_repositories.name \"github_repository_name?\", github_repositories.updated_at \"github_repository_updated_at?\", github_repositories.created_at \"github_repository_created_at?\"\n FROM packages\n LEFT JOIN github_repositories ON packages.github_repository_id = github_repositories.id\n WHERE packages.scope = $1 AND ($2 = true OR packages.is_archived = false) AND ($5 = true OR packages.is_private = false)\n ORDER BY packages.is_archived ASC, packages.name\n OFFSET $3 LIMIT $4", "describe": { "columns": [ { @@ -55,51 +55,56 @@ }, { "ordinal": 8, + "name": "package_is_private", + "type_info": "Bool" + }, + { + "ordinal": 9, "name": "package_updated_at", "type_info": "Timestamptz" }, { - "ordinal": 9, + "ordinal": 10, "name": "package_created_at", "type_info": "Timestamptz" }, { - "ordinal": 10, + "ordinal": 11, "name": "package_version_count!", "type_info": "Int8" }, { - "ordinal": 11, + "ordinal": 12, "name": "package_latest_version", "type_info": "Text" }, { - "ordinal": 12, + "ordinal": 13, "name": "package_version_meta: PackageVersionMeta", "type_info": "Jsonb" }, { - "ordinal": 13, + "ordinal": 14, "name": "github_repository_id?", "type_info": "Int8" }, { - "ordinal": 14, + "ordinal": 15, "name": "github_repository_owner?", "type_info": "Text" }, { - "ordinal": 15, + "ordinal": 16, "name": "github_repository_name?", "type_info": "Text" }, { - "ordinal": 16, + "ordinal": 17, "name": "github_repository_updated_at?", "type_info": "Timestamptz" }, { - "ordinal": 17, + "ordinal": 18, "name": "github_repository_created_at?", "type_info": "Timestamptz" } @@ -109,7 +114,8 @@ "Text", "Bool", "Int8", - "Int8" + "Int8", + "Bool" ] }, "nullable": [ @@ -123,6 +129,7 @@ false, false, false, + false, null, null, null, @@ -133,5 +140,5 @@ false ] }, - "hash": "ce694bc69d1154fa4bc5cc33f2b067f1c06831da03a15512f446c8f146bf120b" + "hash": "bcd2d6abf8d3ff95b1dc96d68db1ea9f49cd312dcf6d4a891d9dbdb46d7ffbbc" } diff --git a/api/.sqlx/query-1fa16ba98cff2cac39f2226eed339e74192378e1f664ab7fa32958fce062aa01.json b/api/.sqlx/query-d2957473c284f6b790cd3e21c1cfe7cf6d7581ad92acced7fcbc7aad0ca28d51.json similarity index 80% rename from api/.sqlx/query-1fa16ba98cff2cac39f2226eed339e74192378e1f664ab7fa32958fce062aa01.json rename to api/.sqlx/query-d2957473c284f6b790cd3e21c1cfe7cf6d7581ad92acced7fcbc7aad0ca28d51.json index dcdad6e73..a8c3367c7 100644 --- a/api/.sqlx/query-1fa16ba98cff2cac39f2226eed339e74192378e1f664ab7fa32958fce062aa01.json +++ b/api/.sqlx/query-d2957473c284f6b790cd3e21c1cfe7cf6d7581ad92acced7fcbc7aad0ca28d51.json @@ -1,6 +1,6 @@ { "db_name": "PostgreSQL", - "query": "UPDATE packages\n SET github_repository_id = NULL\n WHERE scope = $1 AND name = $2\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as \"latest_version\"", + "query": "UPDATE packages\n SET github_repository_id = NULL\n WHERE scope = $1 AND name = $2\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, is_private, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as \"latest_version\"", "describe": { "columns": [ { @@ -55,21 +55,26 @@ }, { "ordinal": 8, + "name": "is_private", + "type_info": "Bool" + }, + { + "ordinal": 9, "name": "updated_at", "type_info": "Timestamptz" }, { - "ordinal": 9, + "ordinal": 10, "name": "created_at", "type_info": "Timestamptz" }, { - "ordinal": 10, + "ordinal": 11, "name": "version_count!", "type_info": "Int8" }, { - "ordinal": 11, + "ordinal": 12, "name": "latest_version", "type_info": "Text" } @@ -91,9 +96,10 @@ false, false, false, + false, null, null ] }, - "hash": "1fa16ba98cff2cac39f2226eed339e74192378e1f664ab7fa32958fce062aa01" + "hash": "d2957473c284f6b790cd3e21c1cfe7cf6d7581ad92acced7fcbc7aad0ca28d51" } diff --git a/api/.sqlx/query-9ee1b77a2fbb5b60b0688552a386dc3c4461f3389285880d028c7e3e10b68acc.json b/api/.sqlx/query-ecc554906f315d9f5f152b9851c0df9094a39a8ab3b5a751f437668c47c3a56f.json similarity index 81% rename from api/.sqlx/query-9ee1b77a2fbb5b60b0688552a386dc3c4461f3389285880d028c7e3e10b68acc.json rename to api/.sqlx/query-ecc554906f315d9f5f152b9851c0df9094a39a8ab3b5a751f437668c47c3a56f.json index ce7e5eb88..9798cdfe4 100644 --- a/api/.sqlx/query-9ee1b77a2fbb5b60b0688552a386dc3c4461f3389285880d028c7e3e10b68acc.json +++ b/api/.sqlx/query-ecc554906f315d9f5f152b9851c0df9094a39a8ab3b5a751f437668c47c3a56f.json @@ -1,6 +1,6 @@ { "db_name": "PostgreSQL", - "query": "UPDATE packages\n SET runtime_compat = $3\n WHERE scope = $1 AND name = $2\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as \"latest_version\"", + "query": "UPDATE packages\n SET runtime_compat = $3\n WHERE scope = $1 AND name = $2\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, is_private, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as \"latest_version\"", "describe": { "columns": [ { @@ -55,21 +55,26 @@ }, { "ordinal": 8, + "name": "is_private", + "type_info": "Bool" + }, + { + "ordinal": 9, "name": "updated_at", "type_info": "Timestamptz" }, { - "ordinal": 9, + "ordinal": 10, "name": "created_at", "type_info": "Timestamptz" }, { - "ordinal": 10, + "ordinal": 11, "name": "version_count!", "type_info": "Int8" }, { - "ordinal": 11, + "ordinal": 12, "name": "latest_version", "type_info": "Text" } @@ -92,9 +97,10 @@ false, false, false, + false, null, null ] }, - "hash": "9ee1b77a2fbb5b60b0688552a386dc3c4461f3389285880d028c7e3e10b68acc" + "hash": "ecc554906f315d9f5f152b9851c0df9094a39a8ab3b5a751f437668c47c3a56f" } diff --git a/api/.sqlx/query-532e3e4dd5ca26105b9cc92f3937ea2c7b486726f9e00245805933a76a0035e7.json b/api/.sqlx/query-f1a90c113e428cb8dfb77979bdef8ba365f1efc2f2ecc9a98e272c25def1def1.json similarity index 69% rename from api/.sqlx/query-532e3e4dd5ca26105b9cc92f3937ea2c7b486726f9e00245805933a76a0035e7.json rename to api/.sqlx/query-f1a90c113e428cb8dfb77979bdef8ba365f1efc2f2ecc9a98e272c25def1def1.json index 63de5b27d..5ae5f3ccb 100644 --- a/api/.sqlx/query-532e3e4dd5ca26105b9cc92f3937ea2c7b486726f9e00245805933a76a0035e7.json +++ b/api/.sqlx/query-f1a90c113e428cb8dfb77979bdef8ba365f1efc2f2ecc9a98e272c25def1def1.json @@ -1,6 +1,6 @@ { "db_name": "PostgreSQL", - "query": "SELECT packages.scope \"package_scope: ScopeName\", packages.name \"package_name: PackageName\", packages.description \"package_description\", packages.github_repository_id \"package_github_repository_id\", packages.runtime_compat \"package_runtime_compat: RuntimeCompat\", packages.readme_source \"package_readme_source: ReadmeSource\", packages.when_featured \"package_when_featured\", packages.is_archived \"package_is_archived\", packages.updated_at \"package_updated_at\", packages.created_at \"package_created_at\",\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = packages.scope AND name = packages.name) as \"package_version_count!\",\n (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_latest_version\",\n (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_version_meta: PackageVersionMeta\",\n github_repositories.id \"github_repository_id?\", github_repositories.owner \"github_repository_owner?\", github_repositories.name \"github_repository_name?\", github_repositories.updated_at \"github_repository_updated_at?\", github_repositories.created_at \"github_repository_created_at?\"\n FROM packages\n LEFT JOIN github_repositories ON packages.github_repository_id = github_repositories.id\n WHERE packages.scope = $1 AND packages.name = $2", + "query": "SELECT packages.scope \"package_scope: ScopeName\", packages.name \"package_name: PackageName\", packages.description \"package_description\", packages.github_repository_id \"package_github_repository_id\", packages.runtime_compat \"package_runtime_compat: RuntimeCompat\", packages.readme_source \"package_readme_source: ReadmeSource\", packages.when_featured \"package_when_featured\", packages.is_archived \"package_is_archived\", packages.is_private \"package_is_private\", packages.updated_at \"package_updated_at\", packages.created_at \"package_created_at\",\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = packages.scope AND name = packages.name) as \"package_version_count!\",\n (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_latest_version\",\n (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"package_version_meta: PackageVersionMeta\",\n github_repositories.id \"github_repository_id?\", github_repositories.owner \"github_repository_owner?\", github_repositories.name \"github_repository_name?\", github_repositories.updated_at \"github_repository_updated_at?\", github_repositories.created_at \"github_repository_created_at?\"\n FROM packages\n LEFT JOIN github_repositories ON packages.github_repository_id = github_repositories.id\n WHERE packages.scope = $1 AND packages.name = $2", "describe": { "columns": [ { @@ -55,51 +55,56 @@ }, { "ordinal": 8, + "name": "package_is_private", + "type_info": "Bool" + }, + { + "ordinal": 9, "name": "package_updated_at", "type_info": "Timestamptz" }, { - "ordinal": 9, + "ordinal": 10, "name": "package_created_at", "type_info": "Timestamptz" }, { - "ordinal": 10, + "ordinal": 11, "name": "package_version_count!", "type_info": "Int8" }, { - "ordinal": 11, + "ordinal": 12, "name": "package_latest_version", "type_info": "Text" }, { - "ordinal": 12, + "ordinal": 13, "name": "package_version_meta: PackageVersionMeta", "type_info": "Jsonb" }, { - "ordinal": 13, + "ordinal": 14, "name": "github_repository_id?", "type_info": "Int8" }, { - "ordinal": 14, + "ordinal": 15, "name": "github_repository_owner?", "type_info": "Text" }, { - "ordinal": 15, + "ordinal": 16, "name": "github_repository_name?", "type_info": "Text" }, { - "ordinal": 16, + "ordinal": 17, "name": "github_repository_updated_at?", "type_info": "Timestamptz" }, { - "ordinal": 17, + "ordinal": 18, "name": "github_repository_created_at?", "type_info": "Timestamptz" } @@ -121,6 +126,7 @@ false, false, false, + false, null, null, null, @@ -131,5 +137,5 @@ false ] }, - "hash": "532e3e4dd5ca26105b9cc92f3937ea2c7b486726f9e00245805933a76a0035e7" + "hash": "f1a90c113e428cb8dfb77979bdef8ba365f1efc2f2ecc9a98e272c25def1def1" } diff --git a/api/.sqlx/query-0ae764ade6ef1d0d5e29732aa68f0c9cf47f1ae339303eb5be8864b5df07e018.json b/api/.sqlx/query-f53e7cd042933a6427086472f9a710b1c00bf0bb5093be0707abb71431716b58.json similarity index 78% rename from api/.sqlx/query-0ae764ade6ef1d0d5e29732aa68f0c9cf47f1ae339303eb5be8864b5df07e018.json rename to api/.sqlx/query-f53e7cd042933a6427086472f9a710b1c00bf0bb5093be0707abb71431716b58.json index edf9d7314..532412b60 100644 --- a/api/.sqlx/query-0ae764ade6ef1d0d5e29732aa68f0c9cf47f1ae339303eb5be8864b5df07e018.json +++ b/api/.sqlx/query-f53e7cd042933a6427086472f9a710b1c00bf0bb5093be0707abb71431716b58.json @@ -1,6 +1,6 @@ { "db_name": "PostgreSQL", - "query": "\n INSERT INTO packages (scope, name)\n VALUES ($1, $2)\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = packages.scope AND name = packages.name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"latest_version\"\n ", + "query": "\n INSERT INTO packages (scope, name)\n VALUES ($1, $2)\n RETURNING scope as \"scope: ScopeName\", name as \"name: PackageName\", description, github_repository_id, runtime_compat as \"runtime_compat: RuntimeCompat\", readme_source as \"readme_source: ReadmeSource\", when_featured, is_archived, is_private, updated_at, created_at,\n (SELECT COUNT(created_at) FROM package_versions WHERE scope = packages.scope AND name = packages.name) as \"version_count!\",\n (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as \"latest_version\"\n ", "describe": { "columns": [ { @@ -55,21 +55,26 @@ }, { "ordinal": 8, + "name": "is_private", + "type_info": "Bool" + }, + { + "ordinal": 9, "name": "updated_at", "type_info": "Timestamptz" }, { - "ordinal": 9, + "ordinal": 10, "name": "created_at", "type_info": "Timestamptz" }, { - "ordinal": 10, + "ordinal": 11, "name": "version_count!", "type_info": "Int8" }, { - "ordinal": 11, + "ordinal": 12, "name": "latest_version", "type_info": "Text" } @@ -91,9 +96,10 @@ false, false, false, + false, null, null ] }, - "hash": "0ae764ade6ef1d0d5e29732aa68f0c9cf47f1ae339303eb5be8864b5df07e018" + "hash": "f53e7cd042933a6427086472f9a710b1c00bf0bb5093be0707abb71431716b58" } diff --git a/api/migrations/20260125100000_private_packages.sql b/api/migrations/20260125100000_private_packages.sql new file mode 100644 index 000000000..15f9b4048 --- /dev/null +++ b/api/migrations/20260125100000_private_packages.sql @@ -0,0 +1,2 @@ +ALTER TABLE packages ADD COLUMN is_private BOOLEAN NOT NULL DEFAULT FALSE; +CREATE INDEX idx_packages_is_private ON packages(scope, is_private); diff --git a/api/src/api/package.rs b/api/src/api/package.rs index bc93efe07..a58bb9197 100644 --- a/api/src/api/package.rs +++ b/api/src/api/package.rs @@ -191,6 +191,7 @@ pub fn package_router() -> Router { util::json(list_publishing_tasks_handler), ) .get("/:package/score", util::json(get_score_handler)) + .get("/:package/check-access", util::auth(check_access_handler)) .build() .unwrap() } @@ -268,8 +269,15 @@ pub async fn list_handler( let iam = req.iam(); let can_see_archived = iam.check_scope_admin_access(&scope).await.is_ok(); + let can_see_private = iam.is_scope_member(&scope).await; let (total, packages) = db - .list_packages_by_scope(&scope, can_see_archived, start, limit) + .list_packages_by_scope( + &scope, + can_see_archived, + can_see_private, + start, + limit, + ) .await?; Ok(ApiList { @@ -343,6 +351,13 @@ pub async fn get_handler(req: Request) -> ApiResult { .await? .ok_or(ApiError::PackageNotFound)?; + if res_package.0.is_private { + let iam = req.iam(); + if !iam.is_scope_member(&scope).await { + return Err(ApiError::PackageNotFound); + } + } + let mut api_package = ApiPackage::from(res_package); if let Some(latest_v) = &api_package.latest_version { @@ -501,6 +516,27 @@ pub async fn update_handler(mut req: Request) -> ApiResult { ) .await?; + Ok(ApiPackage::from((package, repo, meta))) + } + ApiUpdatePackageRequest::IsPrivate(is_private) => { + let package = db + .update_package_is_private( + &user.id, + sudo, + &scope, + &package_name, + is_private, + ) + .await?; + + if let Some(orama_client) = orama_client { + if package.is_private { + orama_client.delete_package(&scope, &package.name); + } else { + orama_client.upsert_package(&package, &meta); + } + } + Ok(ApiPackage::from((package, repo, meta))) } } @@ -656,10 +692,18 @@ pub async fn list_versions_handler( let db = req.data::().unwrap(); - db.get_package(&scope, &package) + let (pkg, _, _) = db + .get_package(&scope, &package) .await? .ok_or(ApiError::PackageNotFound)?; + if pkg.is_private { + let iam = req.iam(); + if !iam.is_scope_member(&scope).await { + return Err(ApiError::PackageNotFound); + } + } + let versions = db .list_package_versions(&scope, &package) .await? @@ -724,11 +768,18 @@ pub async fn get_version_handler( Span::current().record("version", field::display(&version)); let db = req.data::().unwrap(); - let _ = db + let (pkg, _, _) = db .get_package(&scope, &package) .await? .ok_or(ApiError::PackageNotFound)?; + if pkg.is_private { + let iam = req.iam(); + if !iam.is_scope_member(&scope).await { + return Err(ApiError::PackageNotFound); + } + } + let maybe_version = match version { VersionOrLatest::Version(version) => { db.get_package_version(&scope, &package, &version).await? @@ -1177,6 +1228,13 @@ pub async fn get_docs_handler( .await? .ok_or(ApiError::PackageNotFound)?; + if package.is_private { + let iam = req.iam(); + if !iam.is_scope_member(&scope).await { + return Err(ApiError::PackageNotFound); + } + } + let maybe_version = match &version_or_latest { VersionOrLatest::Version(version) => { db.get_package_version(&scope, &package_name, version) @@ -1308,6 +1366,13 @@ pub async fn get_docs_search_handler( .await? .ok_or(ApiError::PackageNotFound)?; + if package.is_private { + let iam = req.iam(); + if !iam.is_scope_member(&scope).await { + return Err(ApiError::PackageNotFound); + } + } + let maybe_version = match &version_or_latest { VersionOrLatest::Version(version) => { db.get_package_version(&scope, &package_name, version) @@ -1379,6 +1444,13 @@ pub async fn get_docs_search_html_handler( .await? .ok_or(ApiError::PackageNotFound)?; + if package.is_private { + let iam = req.iam(); + if !iam.is_scope_member(&scope).await { + return Err(ApiError::PackageNotFound); + } + } + let maybe_version = match &version_or_latest { VersionOrLatest::Version(version) => { db.get_package_version(&scope, &package_name, version) @@ -1458,11 +1530,18 @@ pub async fn get_source_handler( let db = req.data::().unwrap(); let buckets = req.data::().unwrap(); - let _ = db + let (pkg, _, _) = db .get_package(&scope, &package) .await? .ok_or(ApiError::PackageNotFound)?; + if pkg.is_private { + let iam = req.iam(); + if !iam.is_scope_member(&scope).await { + return Err(ApiError::PackageNotFound); + } + } + let maybe_version = match &version_or_latest { VersionOrLatest::Version(version) => { db.get_package_version(&scope, &package, version).await? @@ -1619,10 +1698,18 @@ pub async fn list_dependents_handler( .clamp(1, 10); let db = req.data::().unwrap(); - db.get_package(&scope, &package) + let (pkg, _, _) = db + .get_package(&scope, &package) .await? .ok_or(ApiError::PackageNotFound)?; + if pkg.is_private { + let iam = req.iam(); + if !iam.is_scope_member(&scope).await { + return Err(ApiError::PackageNotFound); + } + } + let (total, deps) = db .list_package_dependents( crate::db::DependencyKind::Jsr, @@ -1655,10 +1742,18 @@ pub async fn get_downloads_handler( Span::current().record("package", field::display(&package)); let db = req.data::().unwrap(); - db.get_package(&scope, &package) + let (pkg, _, _) = db + .get_package(&scope, &package) .await? .ok_or(ApiError::PackageNotFound)?; + if pkg.is_private { + let iam = req.iam(); + if !iam.is_scope_member(&scope).await { + return Err(ApiError::PackageNotFound); + } + } + let current = Utc::now(); let start = current - chrono::Duration::days(90); @@ -1732,6 +1827,17 @@ pub async fn list_dependencies_handler( let db = req.data::().unwrap(); + let (pkg, _, _) = db + .get_package(&scope, &package) + .await? + .ok_or(ApiError::PackageNotFound)?; + if pkg.is_private { + let iam = req.iam(); + if !iam.is_scope_member(&scope).await { + return Err(ApiError::PackageNotFound); + } + } + db.get_package_version(&scope, &package, &version) .await? .ok_or(ApiError::PackageVersionNotFound)?; @@ -2285,6 +2391,19 @@ pub async fn get_dependencies_graph_handler( Span::current().record("package", field::display(&package)); Span::current().record("version", field::display(&version)); + let db = req.data::().unwrap(); + + let (pkg, _, _) = db + .get_package(&scope, &package) + .await? + .ok_or(ApiError::PackageNotFound)?; + if pkg.is_private { + let iam = req.iam(); + if !iam.is_scope_member(&scope).await { + return Err(ApiError::PackageNotFound); + } + } + let buckets = req.data::().unwrap().clone(); let gcs_path = crate::gcs_paths::version_metadata(&scope, &package, &version).into(); @@ -2370,9 +2489,42 @@ pub async fn get_score_handler( .await? .ok_or(ApiError::PackageNotFound)?; + if pkg.is_private { + let iam = req.iam(); + if !iam.is_scope_member(&scope).await { + return Err(ApiError::PackageNotFound); + } + } + Ok(ApiPackageScore::from((&meta, &pkg))) } +#[instrument( + name = "GET /api/scopes/:scope/packages/:package/check-access", + skip(req), + err, + fields(scope, package) +)] +pub async fn check_access_handler( + req: Request, +) -> ApiResult> { + let scope = req.param_scope()?; + let package = req.param_package()?; + + Span::current().record("scope", field::display(&scope)); + Span::current().record("package", field::display(&package)); + + let iam = req.iam(); + + iam.check_package_read_access(&scope, &package).await?; + + let res = Response::builder() + .status(StatusCode::NO_CONTENT) + .body(Body::empty()) + .unwrap(); + Ok(res) +} + #[cfg(test)] mod test { use hyper::Body; diff --git a/api/src/api/self_user.rs b/api/src/api/self_user.rs index b7244fc39..f1f9c0991 100644 --- a/api/src/api/self_user.rs +++ b/api/src/api/self_user.rs @@ -12,11 +12,11 @@ use tracing::instrument; use std::borrow::Cow; use crate::RegistryUrl; -use crate::db::Database; use crate::db::PackagePublishPermission; use crate::db::Permission; use crate::db::TokenType; use crate::db::UserPublic; +use crate::db::{Database, PackageReadPermission}; use crate::emails::EmailArgs; use crate::emails::EmailSender; use crate::iam::ReqIamExt; @@ -241,6 +241,9 @@ async fn create_token( if let Some(email_sender) = email_sender { let permissions = if let Some(permissions) = &token.permissions { match &permissions.0[0] { + Permission::PackagePublish(PackagePublishPermission::Full {}) => { + Cow::Borrowed("Publish new versions to any package in any scope") + } Permission::PackagePublish(PackagePublishPermission::Scope { scope, }) => Cow::Owned(format!( @@ -263,6 +266,22 @@ async fn create_token( "Publish the {} version of the @{}/{} package", version, scope, package )), + Permission::PackageRead(PackageReadPermission::Package { + scope, + package, + }) => Cow::Owned(format!( + "Read the private @{}/{} package", + scope, package + )), + Permission::PackageRead(PackageReadPermission::Scope { scope }) => { + Cow::Owned(format!( + "Read any private package of the @{} scope", + scope + )) + } + Permission::PackageRead(PackageReadPermission::Full {}) => { + Cow::Borrowed("Read any private package in any scope") + } } } else { Cow::Borrowed("Full account access") diff --git a/api/src/api/types.rs b/api/src/api/types.rs index c17befe92..33f8e4a31 100644 --- a/api/src/api/types.rs +++ b/api/src/api/types.rs @@ -454,6 +454,7 @@ pub struct ApiPackage { pub latest_version: Option, pub when_featured: Option>, pub is_archived: bool, + pub is_private: bool, pub readme_source: ApiReadmeSource, } @@ -481,6 +482,7 @@ impl From for ApiPackage { latest_version: package.latest_version, when_featured: package.when_featured, is_archived: package.is_archived, + is_private: package.is_private, readme_source: package.readme_source.into(), } } @@ -501,6 +503,7 @@ pub enum ApiUpdatePackageRequest { ReadmeSource(ApiReadmeSource), IsFeatured(bool), IsArchived(bool), + IsPrivate(bool), } #[derive(Debug, Deserialize, Serialize, Eq, PartialEq)] diff --git a/api/src/buckets.rs b/api/src/buckets.rs index fd53b6646..dd8cef4b2 100644 --- a/api/src/buckets.rs +++ b/api/src/buckets.rs @@ -117,8 +117,10 @@ impl BucketWithQueue { pub struct Buckets { pub publishing_bucket: BucketWithQueue, pub modules_bucket: BucketWithQueue, + pub modules_private_bucket: BucketWithQueue, pub docs_bucket: BucketWithQueue, pub npm_bucket: BucketWithQueue, + pub npm_private_bucket: BucketWithQueue, } struct UploadTask { diff --git a/api/src/config.rs b/api/src/config.rs index ca75aa9ae..e1a9d44bf 100644 --- a/api/src/config.rs +++ b/api/src/config.rs @@ -41,6 +41,22 @@ pub struct Config { /// The name of the GCS bucket where npm tarballs and metadata are stored. pub npm_bucket: String, + #[clap( + long = "modules_private_bucket", + env = "MODULES_PRIVATE_BUCKET", + default_value = "modules-private" + )] + /// The name of the GCS bucket where private module files and metadata is stored. + pub modules_private_bucket: String, + + #[clap( + long = "npm_private_bucket", + env = "NPM_PRIVATE_BUCKET", + default_value = "npm-private" + )] + /// The name of the GCS bucket where private npm tarballs and metadata are stored. + pub npm_private_bucket: String, + #[clap( long = "metadata_strategy", env = "METADATA_STRATEGY", diff --git a/api/src/db/database.rs b/api/src/db/database.rs index 7032ff8fa..9664abeff 100644 --- a/api/src/db/database.rs +++ b/api/src/db/database.rs @@ -488,7 +488,7 @@ impl Database { name: &PackageName, ) -> Result> { sqlx::query!( - r#"SELECT packages.scope "package_scope: ScopeName", packages.name "package_name: PackageName", packages.description "package_description", packages.github_repository_id "package_github_repository_id", packages.runtime_compat "package_runtime_compat: RuntimeCompat", packages.readme_source "package_readme_source: ReadmeSource", packages.when_featured "package_when_featured", packages.is_archived "package_is_archived", packages.updated_at "package_updated_at", packages.created_at "package_created_at", + r#"SELECT packages.scope "package_scope: ScopeName", packages.name "package_name: PackageName", packages.description "package_description", packages.github_repository_id "package_github_repository_id", packages.runtime_compat "package_runtime_compat: RuntimeCompat", packages.readme_source "package_readme_source: ReadmeSource", packages.when_featured "package_when_featured", packages.is_archived "package_is_archived", packages.is_private "package_is_private", packages.updated_at "package_updated_at", packages.created_at "package_created_at", (SELECT COUNT(created_at) FROM package_versions WHERE scope = packages.scope AND name = packages.name) as "package_version_count!", (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as "package_latest_version", (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as "package_version_meta: PackageVersionMeta", @@ -512,6 +512,7 @@ impl Database { latest_version: r.package_latest_version, when_featured: r.package_when_featured, is_archived: r.package_is_archived, + is_private: r.package_is_private, readme_source: r.package_readme_source, }; let github_repository = if r.package_github_repository_id.is_some() { @@ -546,7 +547,7 @@ impl Database { r#" INSERT INTO packages (scope, name) VALUES ($1, $2) - RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, updated_at, created_at, + RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, is_private, updated_at, created_at, (SELECT COUNT(created_at) FROM package_versions WHERE scope = packages.scope AND name = packages.name) as "version_count!", (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as "latest_version" "#, @@ -628,7 +629,7 @@ impl Database { r#"UPDATE packages SET description = $3 WHERE scope = $1 AND name = $2 - RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, updated_at, created_at, + RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, is_private, updated_at, created_at, (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as "version_count!", (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as "latest_version", (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as "package_version_meta: PackageVersionMeta""#, @@ -649,6 +650,7 @@ impl Database { latest_version: r.latest_version, when_featured: r.when_featured, is_archived: r.is_archived, + is_private: r.is_private, readme_source: r.readme_source, }; @@ -708,7 +710,7 @@ impl Database { r#"UPDATE packages SET github_repository_id = $3 WHERE scope = $1 AND name = $2 - RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, updated_at, created_at, + RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, is_private, updated_at, created_at, (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as "version_count!", (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as "latest_version", (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as "package_version_meta: PackageVersionMeta""#, @@ -729,6 +731,7 @@ impl Database { latest_version: r.latest_version, when_featured: r.when_featured, is_archived: r.is_archived, + is_private: r.is_private, readme_source: r.readme_source, }; @@ -773,7 +776,7 @@ impl Database { r#"UPDATE packages SET github_repository_id = NULL WHERE scope = $1 AND name = $2 - RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, updated_at, created_at, + RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, is_private, updated_at, created_at, (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as "version_count!", (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as "latest_version""#, scope as _, @@ -820,7 +823,7 @@ impl Database { r#"UPDATE packages SET runtime_compat = $3 WHERE scope = $1 AND name = $2 - RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, updated_at, created_at, + RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, is_private, updated_at, created_at, (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as "version_count!", (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as "latest_version""#, scope as _, @@ -865,7 +868,7 @@ impl Database { r#"UPDATE packages SET when_featured = $3 WHERE scope = $1 AND name = $2 - RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, updated_at, created_at, + RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, is_private, updated_at, created_at, (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as "version_count!", (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as "latest_version""#, scope as _, @@ -909,7 +912,7 @@ impl Database { r#"UPDATE packages SET is_archived = $3 WHERE scope = $1 AND name = $2 - RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, updated_at, created_at, + RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, is_private, updated_at, created_at, (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as "version_count!", (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as "latest_version""#, scope as _, @@ -924,6 +927,50 @@ impl Database { Ok(package) } + #[instrument(name = "Database::update_package_is_private", skip(self), err)] + pub async fn update_package_is_private( + &self, + actor_id: &Uuid, + is_sudo: bool, + scope: &ScopeName, + name: &PackageName, + is_private: bool, + ) -> Result { + let mut tx = self.pool.begin().await?; + + audit_log( + &mut tx, + actor_id, + is_sudo, + "package_set_private", + json!({ + "scope": scope, + "name": name, + "is_private": is_private, + }), + ) + .await?; + + let package = sqlx::query_as!( + Package, + r#"UPDATE packages + SET is_private = $3 + WHERE scope = $1 AND name = $2 + RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, is_private, updated_at, created_at, + (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as "version_count!", + (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as "latest_version""#, + scope as _, + name as _, + is_private, + ) + .fetch_one(&mut *tx) + .await?; + + tx.commit().await?; + + Ok(package) + } + #[instrument(name = "Database::update_package_source", skip(self), err)] pub async fn update_package_source( &self, @@ -953,7 +1000,7 @@ impl Database { r#"UPDATE packages SET readme_source = $3 WHERE scope = $1 AND name = $2 - RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, updated_at, created_at, + RETURNING scope as "scope: ScopeName", name as "name: PackageName", description, github_repository_id, runtime_compat as "runtime_compat: RuntimeCompat", readme_source as "readme_source: ReadmeSource", when_featured, is_archived, is_private, updated_at, created_at, (SELECT COUNT(created_at) FROM package_versions WHERE scope = scope AND name = name) as "version_count!", (SELECT version FROM package_versions WHERE scope = scope AND name = name ORDER BY version DESC LIMIT 1) as "latest_version""#, scope as _, @@ -1482,26 +1529,28 @@ impl Database { &self, scope: &ScopeName, show_archived: bool, + show_private: bool, start: i64, limit: i64, ) -> Result<(usize, Vec)> { let mut tx = self.pool.begin().await?; let packages = sqlx::query!( - r#"SELECT packages.scope "package_scope: ScopeName", packages.name "package_name: PackageName", packages.description "package_description", packages.github_repository_id "package_github_repository_id", packages.runtime_compat as "package_runtime_compat: RuntimeCompat", packages.readme_source as "package_readme_source: ReadmeSource", packages.when_featured "package_when_featured", packages.is_archived "package_is_archived", packages.updated_at "package_updated_at", packages.created_at "package_created_at", + r#"SELECT packages.scope "package_scope: ScopeName", packages.name "package_name: PackageName", packages.description "package_description", packages.github_repository_id "package_github_repository_id", packages.runtime_compat as "package_runtime_compat: RuntimeCompat", packages.readme_source as "package_readme_source: ReadmeSource", packages.when_featured "package_when_featured", packages.is_archived "package_is_archived", packages.is_private "package_is_private", packages.updated_at "package_updated_at", packages.created_at "package_created_at", (SELECT COUNT(created_at) FROM package_versions WHERE scope = packages.scope AND name = packages.name) as "package_version_count!", (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as "package_latest_version", (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as "package_version_meta: PackageVersionMeta", github_repositories.id "github_repository_id?", github_repositories.owner "github_repository_owner?", github_repositories.name "github_repository_name?", github_repositories.updated_at "github_repository_updated_at?", github_repositories.created_at "github_repository_created_at?" FROM packages LEFT JOIN github_repositories ON packages.github_repository_id = github_repositories.id - WHERE packages.scope = $1 AND ($2 = true OR packages.is_archived = false) + WHERE packages.scope = $1 AND ($2 = true OR packages.is_archived = false) AND ($5 = true OR packages.is_private = false) ORDER BY packages.is_archived ASC, packages.name OFFSET $3 LIMIT $4"#, scope as _, show_archived, start, - limit + limit, + show_private, ) .map(|r| { let package = Package { @@ -1516,6 +1565,7 @@ impl Database { latest_version: r.package_latest_version, when_featured: r.package_when_featured, is_archived: r.package_is_archived, + is_private: r.package_is_private, readme_source: r.package_readme_source, }; let github_repository = if r.package_github_repository_id.is_some() { @@ -1538,9 +1588,10 @@ impl Database { .await?; let total_packages = sqlx::query!( - r#"SELECT COUNT(created_at) FROM packages WHERE scope = $1 AND ($2 = true OR packages.is_archived = false);"#, + r#"SELECT COUNT(created_at) FROM packages WHERE scope = $1 AND ($2 = true OR packages.is_archived = false) AND ($3 = true OR packages.is_private = false);"#, scope as _, show_archived, + show_private, ) .map(|r| r.count.unwrap()) .fetch_one(&mut *tx) @@ -1615,14 +1666,14 @@ impl Database { } || "packages.name ASC, packages.scope ASC"); let packages = sqlx::query( - &format!(r#"SELECT packages.scope "package_scope", packages.name "package_name", packages.description "package_description", packages.github_repository_id "package_github_repository_id", packages.runtime_compat as "package_runtime_compat", packages.when_featured "package_when_featured", packages.readme_source "package_readme_source", packages.is_archived "package_is_archived", packages.updated_at "package_updated_at", packages.created_at "package_created_at", + &format!(r#"SELECT packages.scope "package_scope", packages.name "package_name", packages.description "package_description", packages.github_repository_id "package_github_repository_id", packages.runtime_compat as "package_runtime_compat", packages.when_featured "package_when_featured", packages.readme_source "package_readme_source", packages.is_archived "package_is_archived", packages.is_private "package_is_private", packages.updated_at "package_updated_at", packages.created_at "package_created_at", (SELECT COUNT(created_at) FROM package_versions WHERE scope = packages.scope AND name = packages.name) as "package_version_count", (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as "package_latest_version", (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as "package_version_meta", github_repositories.id "github_repository_id", github_repositories.owner "github_repository_owner", github_repositories.name "github_repository_name", github_repositories.updated_at "github_repository_updated_at", github_repositories.created_at "github_repository_created_at" FROM packages LEFT JOIN github_repositories ON packages.github_repository_id = github_repositories.id - WHERE (packages.scope ILIKE $1 OR packages.name ILIKE $2) AND (packages.github_repository_id = $5 OR $5 IS NULL) AND NOT packages.is_archived + WHERE (packages.scope ILIKE $1 OR packages.name ILIKE $2) AND (packages.github_repository_id = $5 OR $5 IS NULL) AND NOT packages.is_archived AND NOT packages.is_private ORDER BY CASE WHEN packages.name ILIKE $3 THEN 1 -- Exact match for package name @@ -1678,14 +1729,14 @@ impl Database { Vec, )> { let newest = sqlx::query!( - r#"SELECT packages.scope "package_scope: ScopeName", packages.name "package_name: PackageName", packages.description "package_description", packages.github_repository_id "package_github_repository_id", packages.runtime_compat as "package_runtime_compat: RuntimeCompat", packages.readme_source as "package_readme_source: ReadmeSource", packages.when_featured "package_when_featured", packages.is_archived "package_is_archived", packages.updated_at "package_updated_at", packages.created_at "package_created_at", + r#"SELECT packages.scope "package_scope: ScopeName", packages.name "package_name: PackageName", packages.description "package_description", packages.github_repository_id "package_github_repository_id", packages.runtime_compat as "package_runtime_compat: RuntimeCompat", packages.readme_source as "package_readme_source: ReadmeSource", packages.when_featured "package_when_featured", packages.is_archived "package_is_archived", packages.is_private "package_is_private", packages.updated_at "package_updated_at", packages.created_at "package_created_at", (SELECT COUNT(created_at) FROM package_versions WHERE scope = packages.scope AND name = packages.name) as "package_version_count!", (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as "package_latest_version", (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as "package_version_meta: PackageVersionMeta", github_repositories.id "github_repository_id?", github_repositories.owner "github_repository_owner?", github_repositories.name "github_repository_name?", github_repositories.updated_at "github_repository_updated_at?", github_repositories.created_at "github_repository_created_at?" FROM packages LEFT JOIN github_repositories ON packages.github_repository_id = github_repositories.id - WHERE (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND is_yanked = false AND version IS NOT NULL ORDER BY version DESC LIMIT 1) IS NOT NULL AND NOT packages.is_archived + WHERE (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND is_yanked = false AND version IS NOT NULL ORDER BY version DESC LIMIT 1) IS NOT NULL AND NOT packages.is_archived AND NOT packages.is_private ORDER BY packages.created_at DESC LIMIT 10"#, ) @@ -1702,6 +1753,7 @@ impl Database { latest_version: r.package_latest_version, when_featured: r.package_when_featured, is_archived: r.package_is_archived, + is_private: r.package_is_private, readme_source: r.package_readme_source, }; let github_repository = if r.package_github_repository_id.is_some() { @@ -1738,7 +1790,7 @@ impl Database { AND dl.version = package_versions.version) as "lifetime_download_count!" FROM package_versions JOIN packages ON packages.scope = package_versions.scope AND packages.name = package_versions.name - WHERE NOT packages.is_archived + WHERE NOT packages.is_archived AND NOT packages.is_private ORDER BY package_versions.created_at DESC LIMIT 10"#, ) @@ -1746,14 +1798,14 @@ impl Database { .await?; let featured = sqlx::query!( - r#"SELECT packages.scope "package_scope: ScopeName", packages.name "package_name: PackageName", packages.description "package_description", packages.github_repository_id "package_github_repository_id", packages.runtime_compat as "package_runtime_compat: RuntimeCompat", packages.readme_source as "package_readme_source: ReadmeSource", packages.when_featured "package_when_featured", packages.is_archived "package_is_archived", packages.updated_at "package_updated_at", packages.created_at "package_created_at", + r#"SELECT packages.scope "package_scope: ScopeName", packages.name "package_name: PackageName", packages.description "package_description", packages.github_repository_id "package_github_repository_id", packages.runtime_compat as "package_runtime_compat: RuntimeCompat", packages.readme_source as "package_readme_source: ReadmeSource", packages.when_featured "package_when_featured", packages.is_archived "package_is_archived", packages.is_private "package_is_private", packages.updated_at "package_updated_at", packages.created_at "package_created_at", (SELECT COUNT(created_at) FROM package_versions WHERE scope = packages.scope AND name = packages.name) as "package_version_count!", (SELECT version FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as "package_latest_version", (SELECT meta FROM package_versions WHERE scope = packages.scope AND name = packages.name AND version NOT LIKE '%-%' AND is_yanked = false ORDER BY version DESC LIMIT 1) as "package_version_meta: PackageVersionMeta", github_repositories.id "github_repository_id?", github_repositories.owner "github_repository_owner?", github_repositories.name "github_repository_name?", github_repositories.updated_at "github_repository_updated_at?", github_repositories.created_at "github_repository_created_at?" FROM packages LEFT JOIN github_repositories ON packages.github_repository_id = github_repositories.id - WHERE packages.when_featured IS NOT NULL AND NOT packages.is_archived + WHERE packages.when_featured IS NOT NULL AND NOT packages.is_archived AND NOT packages.is_private ORDER BY packages.when_featured DESC LIMIT 10"#, ) @@ -1770,6 +1822,7 @@ impl Database { latest_version: r.package_latest_version, when_featured: r.package_when_featured, is_archived: r.package_is_archived, + is_private: r.package_is_private, readme_source: r.package_readme_source, }; let github_repository = if r.package_github_repository_id.is_some() { diff --git a/api/src/db/models.rs b/api/src/db/models.rs index f6e959933..6ee055be8 100644 --- a/api/src/db/models.rs +++ b/api/src/db/models.rs @@ -349,6 +349,7 @@ pub struct Package { pub latest_version: Option, pub when_featured: Option>, pub is_archived: bool, + pub is_private: bool, pub readme_source: ReadmeSource, } @@ -394,6 +395,7 @@ impl FromRow<'_, sqlx::postgres::PgRow> for Package { "package_when_featured", )?, is_archived: try_get_row_or(row, "is_archived", "package_is_archived")?, + is_private: try_get_row_or(row, "is_private", "package_is_private")?, readme_source: try_get_row_or( row, "readme_source", @@ -624,6 +626,8 @@ pub struct Permissions(pub Vec); pub enum Permission { #[serde(rename = "package/publish")] PackagePublish(PackagePublishPermission), + #[serde(rename = "package/read")] + PackageRead(PackageReadPermission), } #[derive(Debug, Clone, Deserialize, Serialize)] @@ -643,6 +647,24 @@ pub enum PackagePublishPermission { }, #[serde(rename_all = "camelCase")] Scope { scope: ScopeName }, + // needs to be an empty struct variant for serde to work correctly + #[serde(rename_all = "camelCase")] + Full {}, +} + +#[derive(Debug, Clone, Deserialize, Serialize)] +#[serde(untagged)] +pub enum PackageReadPermission { + #[serde(rename_all = "camelCase")] + Package { + scope: ScopeName, + package: PackageName, + }, + #[serde(rename_all = "camelCase")] + Scope { scope: ScopeName }, + // needs to be an empty struct variant for serde to work correctly + #[serde(rename_all = "camelCase")] + Full {}, } impl sqlx::Decode<'_, sqlx::Postgres> for Permissions { diff --git a/api/src/iam.rs b/api/src/iam.rs index da1079a2a..6493d3913 100644 --- a/api/src/iam.rs +++ b/api/src/iam.rs @@ -7,6 +7,7 @@ use uuid::Uuid; use crate::api::ApiError; use crate::db::Database; use crate::db::PackagePublishPermission; +use crate::db::PackageReadPermission; use crate::db::Permission; use crate::db::Permissions; use crate::db::Token; @@ -96,6 +97,26 @@ impl<'s> IamHandler<'s> { } } + /// Returns true if the current user is a scope member (or staff using sudo). + /// Returns false for anonymous users or non-members. + pub async fn is_scope_member(&self, scope: &ScopeName) -> bool { + match &self.principal { + Principal::User(user) => { + if user.is_staff && self.sudo { + return true; + } + self + .db + .get_scope_member(scope, user.id) + .await + .ok() + .flatten() + .is_some() + } + Principal::GitHubActions { .. } | Principal::Anonymous => false, + } + } + pub async fn check_scope_member_delete_access( &self, scope: &ScopeName, @@ -251,6 +272,73 @@ impl<'s> IamHandler<'s> { Principal::Anonymous => Err(ApiError::MissingAuthentication), } } + + pub async fn check_package_read_access( + &self, + scope: &ScopeName, + package: &PackageName, + ) -> Result, ApiError> { + let (pkg, _, _) = self + .db + .get_package(scope, package) + .await? + .ok_or(ApiError::PackageNotFound)?; + + if !pkg.is_private { + return Ok(match &self.principal { + Principal::User(user) => Some(user), + _ => None, + }); + } + + if let Some(permissions) = &self.permissions { + let has_read_permission = permissions.0.iter().any(|permission| { + if let Permission::PackageRead(read) = permission { + match read { + PackageReadPermission::Package { + scope: perm_scope, + package: perm_package, + } => perm_scope == scope && perm_package == package, + PackageReadPermission::Scope { scope: perm_scope } => { + perm_scope == scope + } + PackageReadPermission::Full {} => true, + } + } else { + false + } + }); + if !has_read_permission { + return Err(ApiError::MissingPermission); + } + } + + match &self.principal { + Principal::User(user) => { + // Check if user is a scope member + if self.db.get_scope_member(scope, user.id).await?.is_some() { + Ok(Some(user)) + } else if user.is_staff && self.sudo { + Ok(Some(user)) + } else { + Err(ApiError::ActorNotScopeMember) + } + } + Principal::GitHubActions { user, .. } => { + // GitHub Actions can access if the user is a scope member + if let Some(user) = user { + if self.db.get_scope_member(scope, user.id).await?.is_some() { + Ok(Some(user)) + } else { + Err(ApiError::ActorNotScopeMember) + } + } else { + Err(ApiError::ActorNotScopeMember) + } + } + Principal::Anonymous => Err(ApiError::MissingAuthentication), + } + } } pub struct PublishAccessRestriction { diff --git a/api/src/main.rs b/api/src/main.rs index c4edcfb55..b8e5bee51 100644 --- a/api/src/main.rs +++ b/api/src/main.rs @@ -178,13 +178,25 @@ async fn main() { let npm_bucket = BucketWithQueue::new(gcp::Bucket::new( gcp_client.clone(), config.npm_bucket, + config.gcs_endpoint.clone(), + )); + let modules_private_bucket = BucketWithQueue::new(gcp::Bucket::new( + gcp_client.clone(), + config.modules_private_bucket, + config.gcs_endpoint.clone(), + )); + let npm_private_bucket = BucketWithQueue::new(gcp::Bucket::new( + gcp_client.clone(), + config.npm_private_bucket, config.gcs_endpoint, )); let buckets = Buckets { publishing_bucket, modules_bucket: modules_bucket.clone(), + modules_private_bucket, docs_bucket, npm_bucket, + npm_private_bucket, }; let publish_queue = config diff --git a/api/src/orama.rs b/api/src/orama.rs index efb3ce861..6596db871 100644 --- a/api/src/orama.rs +++ b/api/src/orama.rs @@ -54,7 +54,7 @@ impl OramaClient { #[instrument(name = "OramaClient::upsert_package", skip(self))] pub fn upsert_package(&self, package: &Package, meta: &PackageVersionMeta) { - if package.version_count == 0 || package.is_archived { + if package.version_count == 0 || package.is_archived || package.is_private { return; } diff --git a/api/src/publish.rs b/api/src/publish.rs index e6c6b8b80..1f0c13552 100644 --- a/api/src/publish.rs +++ b/api/src/publish.rs @@ -122,9 +122,34 @@ pub async fn publish_task( return Err(ApiError::InternalServerError); } PublishingTaskStatus::Processed => { - upload_package_manifest(&db, &buckets, &publishing_task).await?; - upload_npm_version_manifest(&db, &buckets, &npm_url, &publishing_task) - .await?; + let (package, _, _) = db + .get_package( + &publishing_task.package_scope, + &publishing_task.package_name, + ) + .await? + .ok_or_else(|| { + error!( + "package not found during manifest upload: {}/{}", + &publishing_task.package_scope, &publishing_task.package_name + ); + ApiError::InternalServerError + })?; + upload_package_manifest( + &db, + &buckets, + &publishing_task, + package.is_private, + ) + .await?; + upload_npm_version_manifest( + &db, + &buckets, + &npm_url, + &publishing_task, + package.is_private, + ) + .await?; publishing_task = db .update_publishing_task_status( None, @@ -237,11 +262,22 @@ async fn process_publishing_task( .await?; if let Some(orama_client) = orama_client { - orama_client.upsert_symbols( - &publishing_task.package_scope, - &publishing_task.package_name, - doc_search_json, - ); + let (package, _, _) = db + .get_package( + &publishing_task.package_scope, + &publishing_task.package_name, + ) + .await? + .ok_or_else(|| { + anyhow::anyhow!("package not found during symbol indexing") + })?; + if !package.is_private { + orama_client.upsert_symbols( + &publishing_task.package_scope, + &publishing_task.package_name, + doc_search_json, + ); + } } Ok(()) @@ -371,6 +407,7 @@ async fn upload_package_manifest( db: &Database, buckets: &Buckets, publishing_task: &PublishingTask, + is_private: bool, ) -> Result<(), anyhow::Error> { let package_metadata_gcs_path = crate::gcs_paths::package_metadata( &publishing_task.package_scope, @@ -383,8 +420,12 @@ async fn upload_package_manifest( ) .await?; let content = serde_json::to_vec(&package_metadata)?; - buckets - .modules_bucket + let modules_bucket = if is_private { + &buckets.modules_private_bucket + } else { + &buckets.modules_bucket + }; + modules_bucket .upload( package_metadata_gcs_path.into(), UploadTaskBody::Bytes(content.into()), @@ -404,6 +445,7 @@ async fn upload_npm_version_manifest( buckets: &Buckets, npm_url: &Url, publishing_task: &PublishingTask, + is_private: bool, ) -> Result<(), anyhow::Error> { let npm_version_manifest_path_gcs_path = crate::gcs_paths::npm_version_manifest_path( @@ -418,8 +460,12 @@ async fn upload_npm_version_manifest( ) .await?; let content = serde_json::to_vec_pretty(&npm_version_manifest)?; - buckets - .npm_bucket + let npm_bucket = if is_private { + &buckets.npm_private_bucket + } else { + &buckets.npm_bucket + }; + npm_bucket .upload( npm_version_manifest_path_gcs_path.into(), UploadTaskBody::Bytes(content.into()), diff --git a/api/src/tarball.rs b/api/src/tarball.rs index 35531c2fc..0d1c35a49 100644 --- a/api/src/tarball.rs +++ b/api/src/tarball.rs @@ -33,9 +33,10 @@ use crate::analysis::analyze_package; use crate::buckets::Buckets; use crate::buckets::UploadTaskBody; use crate::db::Database; +use crate::db::DependencyKind; use crate::db::ExportsMap; +use crate::db::PackageVersionMeta; use crate::db::PublishingTask; -use crate::db::{DependencyKind, PackageVersionMeta}; use crate::gcp::CACHE_CONTROL_IMMUTABLE; use crate::gcp::GcsError; use crate::gcp::GcsUploadOptions; @@ -89,6 +90,20 @@ pub async fn process_tarball( registry_url: Url, publishing_task: &PublishingTask, ) -> Result { + let (package, _, _) = db + .get_package( + &publishing_task.package_scope, + &publishing_task.package_name, + ) + .await? + .ok_or(PublishError::PackageNotFound)?; + + let (modules_bucket, npm_bucket) = if package.is_private { + (&buckets.modules_private_bucket, &buckets.npm_private_bucket) + } else { + (&buckets.modules_bucket, &buckets.npm_bucket) + }; + let tarball_path = gcs_tarball_path(publishing_task.id); let stream = buckets .publishing_bucket @@ -383,8 +398,7 @@ pub async fn process_tarball( &publishing_task.package_version, NPM_TARBALL_REVISION, ); - buckets - .npm_bucket + npm_bucket .upload( npm_tarball_path.into(), UploadTaskBody::Bytes(Bytes::from(npm_tarball.tarball)), @@ -429,8 +443,7 @@ pub async fn process_tarball( ); async move { - buckets - .modules_bucket + modules_bucket .upload( gcs_path.into(), UploadTaskBody::Bytes(bytes), @@ -476,6 +489,9 @@ pub enum PublishError { #[error("missing tarball")] MissingTarball, + #[error("package not found")] + PackageNotFound, + #[error("gcs upload error: {0}")] GcsUploadError(GcsError), @@ -696,6 +712,7 @@ impl PublishError { PublishError::InvalidJsrDependencySubPath { .. } => { Some("invalidJsrDependencySubPath") } + PublishError::PackageNotFound => Some("packageNotFound"), } } } diff --git a/api/src/util.rs b/api/src/util.rs index c106479a6..adee44fee 100644 --- a/api/src/util.rs +++ b/api/src/util.rs @@ -472,13 +472,17 @@ pub mod test { let gcs = FakeGcsTester::new().await; let publishing_bucket = gcs.create_bucket("publishing").await; let modules_bucket = gcs.create_bucket("modules").await; + let modules_private_bucket = gcs.create_bucket("modules-private").await; let docs_bucket = gcs.create_bucket("docs").await; let npm_bucket = gcs.create_bucket("npm").await; + let npm_private_bucket = gcs.create_bucket("npm-private").await; let buckets = Buckets { publishing_bucket: BucketWithQueue::new(publishing_bucket), modules_bucket: BucketWithQueue::new(modules_bucket), + modules_private_bucket: BucketWithQueue::new(modules_private_bucket), docs_bucket: BucketWithQueue::new(docs_bucket), npm_bucket: BucketWithQueue::new(npm_bucket), + npm_private_bucket: BucketWithQueue::new(npm_private_bucket), }; let github_oauth2_client = GithubOauth2Client::new( oauth2::ClientId::new("".to_string()), diff --git a/deno.lock b/deno.lock index 1526b1974..a2d61fa93 100644 --- a/deno.lock +++ b/deno.lock @@ -7,6 +7,9 @@ "jsr:@deno/graph@0.86": "0.86.9", "jsr:@deno/graph@~0.82.3": "0.82.3", "jsr:@denosaurs/emoji@0.3": "0.3.1", + "jsr:@foo/bar@*": "0.0.2", + "jsr:@scope/foo@*": "1.2.3", + "jsr:@std/assert@^1.0.17": "1.0.17", "jsr:@std/async@^1.0.8": "1.0.9", "jsr:@std/bytes@^1.0.5": "1.0.6", "jsr:@std/bytes@^1.0.6": "1.0.6", @@ -18,6 +21,7 @@ "jsr:@std/fmt@^1.0.8": "1.0.8", "jsr:@std/front-matter@^1.0.5": "1.0.5", "jsr:@std/fs@^1.0.6": "1.0.19", + "jsr:@std/internal@^1.0.12": "1.0.12", "jsr:@std/io@0.225": "0.225.2", "jsr:@std/path@^1.0.8": "1.0.8", "jsr:@std/toml@^1.0.1": "1.0.2", @@ -75,6 +79,21 @@ "@denosaurs/emoji@0.3.1": { "integrity": "b0aed5f55dec99e83da7c9637fe0a36d1d6252b7c99deaaa3fc5dea3fcf3da8b" }, + "@foo/bar@0.0.2": { + "integrity": "73a5cd2c7a0de2d0cf85429e177482dc5f215ce797aaed6aa9bb2ec339268455", + "dependencies": [ + "jsr:@std/assert" + ] + }, + "@scope/foo@1.2.3": { + "integrity": "aaf76d364e8f7ffc416c76c971772be87388eef8c5407dd50dbd96d6dc1d6ec6" + }, + "@std/assert@1.0.17": { + "integrity": "df5ebfffe77c03b3fa1401e11c762cc8f603d51021c56c4d15a8c7ab45e90dbe", + "dependencies": [ + "jsr:@std/internal" + ] + }, "@std/async@1.0.9": { "integrity": "c6472fd0623b3f3daae023cdf7ca5535e1b721dfbf376562c0c12b3fb4867f91" }, @@ -106,6 +125,9 @@ "@std/fs@1.0.19": { "integrity": "051968c2b1eae4d2ea9f79a08a3845740ef6af10356aff43d3e2ef11ed09fb06" }, + "@std/internal@1.0.12": { + "integrity": "972a634fd5bc34b242024402972cd5143eac68d8dffaca5eaa4dba30ce17b027" + }, "@std/io@0.225.2": { "integrity": "3c740cd4ee4c082e6cfc86458f47e2ab7cb353dc6234d5e9b1f91a2de5f4d6c7", "dependencies": [ diff --git a/frontend/components/PackageHit.tsx b/frontend/components/PackageHit.tsx index 00c111139..0067394a7 100644 --- a/frontend/components/PackageHit.tsx +++ b/frontend/components/PackageHit.tsx @@ -4,7 +4,8 @@ import type { Package, RuntimeCompat } from "../utils/api_types.ts"; import { getScoreBgColorClass } from "../utils/score_ring_color.ts"; import type { ListDisplayItem } from "./List.tsx"; import { RuntimeCompatIndicator } from "./RuntimeCompatIndicator.tsx"; -import TbArchive from "tb-icons/TbArchive"; +import TbArchiveFilled from "tb-icons/TbArchiveFilled"; +import TbLockFilled from "tb-icons/TbLockFilled"; const runtimeCompatExists = (compat: RuntimeCompat) => { return compat?.browser || compat?.deno || compat?.node || compat?.workerd || @@ -28,10 +29,16 @@ export function PackageHit(pkg: OramaPackageHit | Package): ListDisplayItem { )} {(pkg as Package).isArchived && (
- + Archived
)} + {(pkg as Package).isPrivate && ( +
+ + Private +
+ )}
{pkg.description} diff --git a/frontend/routes/account/tokens/(_islands)/CreateToken.tsx b/frontend/routes/account/tokens/(_islands)/CreateToken.tsx index 045fc94ae..930c0d095 100644 --- a/frontend/routes/account/tokens/(_islands)/CreateToken.tsx +++ b/frontend/routes/account/tokens/(_islands)/CreateToken.tsx @@ -1,4 +1,5 @@ // Copyright 2024 the JSR authors. All rights reserved. MIT license. +import type { ComponentChildren } from "preact"; import { useCallback, useEffect, useRef } from "preact/hooks"; import { Signal, useComputed, useSignal } from "@preact/signals"; import { IS_BROWSER } from "fresh/runtime"; @@ -10,46 +11,107 @@ import { CreatedToken, Permission } from "../../../../utils/api_types.ts"; import { ErrorDisplay } from "../../../../components/ErrorDisplay.tsx"; export function CreateToken() { - const usage = useSignal<"publish" | "api" | null>(null); + const usage = useSignal<"publish" | "read" | "api" | null>(null); + + switch (usage.value) { + case null: + return ; + case "publish": + return ; + case "read": + return ; + case "api": + return ; + } +} + +function PublishTokenFlow() { const env = useSignal< "development" | "github_actions" | "other_ci_service" | null >(null); const localMachineAnyway = useSignal(false); - const willStoreSafely = useSignal(false); const willBeSafe = useSignal(false); - if (usage.value === null) { - return ; - } - - if (usage.value === "publish" && env.value === null) { + if (env.value === null) { return ; } - if ( - usage.value === "publish" && env.value === "development" && - !localMachineAnyway.value - ) { + if (env.value === "development" && !localMachineAnyway.value) { return ; } - if (usage.value === "publish" && env.value === "github_actions") { + if (env.value === "github_actions") { return ; } - if ( - !willStoreSafely.value && - (usage.value === "api" || - (usage.value === "publish" && env.value !== "other_ci_service")) - ) { - return ; + if (!willBeSafe.value) { + return ( + + + Personal access tokens enable a malicious user to impersonate you and + publish new versions of your packages + + + ); } + return ( + + ); +} + +function ReadTokenFlow() { + const willBeSafe = useSignal(false); + if (!willBeSafe.value) { - return ; + return ( + + + Personal access tokens enable a malicious user to read private + packages you have access to. + + + ); } - return ; + return ( + + ); +} + +function ApiTokenFlow() { + const willBeSafe = useSignal(false); + + if (!willBeSafe.value) { + return ( + + Personal access tokens enable a malicious user to impersonate you and + perform any action you can on JSR,{" "} + + including publishing new versions of your packages + . + + ); + } + + return ; } function useRadioGroup( @@ -84,7 +146,9 @@ function useRadioGroup( return { ref, disabled, onSubmit, onInput }; } -function ChooseUsage({ usage }: { usage: Signal<"publish" | "api" | null> }) { +function ChooseUsage( + { usage }: { usage: Signal<"publish" | "read" | "api" | null> }, +) { const { ref, disabled, onSubmit, onInput } = useRadioGroup("path", usage); return ( @@ -97,6 +161,10 @@ function ChooseUsage({ usage }: { usage: Signal<"publish" | "api" | null> }) { Publish packages +