| @@ -72,15 +72,40 @@ fn counts(index: &Index, did: &str, key: &str) -> (Option<u64>, Option<u64>) { |
| | (index.star_count(did, key).ok(), forks) |
| | } |
| | |
| | /// What each private repository was last counted as mostly written in, |
| | /// by its owner's DID and its key. |
| | static PRIVATE_LANGUAGES: LazyLock<Mutex<Counted>> = LazyLock::new(Default::default); |
| | |
| | /// What each repository was counted as written in, by its owner's DID and |
| | /// its key. |
| | type Counted = HashMap<(String, String), Option<Language>>; |
| | |
| | /// What `did`'s repository `r` is mostly written in. A public one's is |
| | /// the index's, counted as its refs move ([`languages::follow`]): one never |
| | /// counted is asked for, for a later read, rather than waited on. A |
| | /// private one, which the index never sees, is counted from its mirror. |
| | async fn language(app: &App, did: &str, r: &RepoRecord, private: bool) -> Option<LanguageView> { |
| | /// private one, which the index never sees, is counted from its mirror: |
| | /// once counted, what was counted shows while its mirror syncs and it is |
| | /// counted again in the background, as a sync may wait a second on its |
| | /// owner's PDS. |
| | async fn language( |
| | app: &Arc<App>, |
| | did: &str, |
| | r: &RepoRecord, |
| | private: bool, |
| | ) -> Option<LanguageView> { |
| | if private { |
| | let git = app.mirror(did, &r.name).await.ok()?; |
| | let objects = objects::open(&git.dir).ok()?; |
| | return languages::main_of(&objects).map(LanguageView::from); |
| | let key = (did.to_string(), r.key.clone()); |
| | let count = count_private(app.clone(), key.clone(), r.name.clone()); |
| | let kept = PRIVATE_LANGUAGES.lock().unwrap().get(&key).cloned(); |
| | let found = match kept { |
| | Some(kept) => { |
| | let viewer = crate::private::viewer(); |
| | tokio::spawn(crate::private::reading(viewer, None, count)); |
| | kept |
| | } |
| | None => count.await, |
| | }; |
| | return found.map(LanguageView::from); |
| | } |
| | let index = app.index.as_ref()?; |
| | let kept = index.language(did, &r.key).ok().flatten(); |
| @@ -91,6 +116,17 @@ async fn language(app: &App, did: &str, r: &RepoRecord, private: bool) -> Option |
| | found.map(LanguageView::from) |
| | } |
| | |
| | /// Counts what the private repository named `name`, of the owner and key |
| | /// `key` names, is mostly written in, from its mirror synced, and keeps it. |
| | async fn count_private(app: Arc<App>, key: (String, String), name: String) -> Option<Language> { |
| | let git = app.mirror(&key.0, &name).await.ok()?; |
| | let objects = objects::open(&git.dir).ok()?; |
| | let found = languages::main_of(&objects); |
| | let mut kept = PRIVATE_LANGUAGES.lock().unwrap(); |
| | kept.insert(key, found.clone()); |
| | found |
| | } |
| | |
| | #[derive(Serialize)] |
| | pub struct Output { |
| | repos: Vec<RepoView>, |
| @@ -336,7 +372,7 @@ pub async fn get_actor_stars( |
| | } |
| | } |
| | |
| | async fn starred(app: &App, index: &Index, did: &str) -> Result<axum::Json<Output>> { |
| | async fn starred(app: &Arc<App>, index: &Index, did: &str) -> Result<axum::Json<Output>> { |
| | let found = index |
| | .actor_stars(did) |
| | .map_err(anyhow::Error::from) |
| |