~/selfhut

selfhut/src/git/file.rs -rw-r--r-- 3.33 kB
e22778fe — Arthur Melton fix code 2 years ago

            
7dbdfabf arthurmelton
7dbdfabf arthurmelton
00c0a257 Arthur Melton
e22778fe Arthur Melton
7dbdfabf arthurmelton
0016c2cc arthurmelton
7dbdfabf arthurmelton
7dbdfabf arthurmelton
00c0a257 Arthur Melton
7dbdfabf arthurmelton
00c0a257 Arthur Melton
7dbdfabf arthurmelton
00c0a257 Arthur Melton
7dbdfabf arthurmelton
00c0a257 Arthur Melton
7dbdfabf arthurmelton
0016c2cc arthurmelton
7dbdfabf arthurmelton
7dbdfabf arthurmelton
00c0a257 Arthur Melton
7dbdfabf arthurmelton
00c0a257 Arthur Melton
7dbdfabf arthurmelton
00c0a257 Arthur Melton
7dbdfabf arthurmelton
00c0a257 Arthur Melton
19f9b68c arthurmelton
7dbdfabf arthurmelton
7dbdfabf arthurmelton
00c0a257 Arthur Melton
7dbdfabf arthurmelton
0016c2cc arthurmelton
7dbdfabf arthurmelton
00c0a257 Arthur Melton
7dbdfabf arthurmelton





























































1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
use crate::config::CONFIG;
use git2::ObjectType;
use humansize::{format_size, DECIMAL};
use serde_derive::Serialize;

use std::path::PathBuf;

pub fn files(repo: String, branch: String, path: String) -> Option<Vec<File>> {
    if branch.contains(":") {
        return None;
    }
    let mut repo_path = CONFIG.git_location.clone();
    repo_path.push(format!("{}.git", repo));
    let repo = git2::Repository::open(repo_path).ok()?;
    let obj = repo.revparse_single(&format!("{}:{}", branch, path)).ok()?;
    let mut returns = Vec::new();
    match obj.kind() {
        Some(ObjectType::Tree) => {
            let tree = obj.as_tree()?;
            for entry in tree.iter() {
                returns.push(File {
                    name: entry.name()?.to_string(),
                    size: match entry.kind() {
                        Some(ObjectType::Blob) => Some(format_size(
                            entry.to_object(&repo).ok()?.into_blob().ok()?.size(),
                            DECIMAL,
                        )),
                        _ => None,
                    },
                    file_type: match entry.kind() {
                        Some(ObjectType::Blob) => FileType::blob,
                        _ => FileType::tree,
                    },
                    properties: unix_mode::to_string(entry.filemode() as u32),
                    properties_int: entry.filemode(),
                })
            }
        }
        _ => {
            return None;
        }
    }
    Some(returns)
}

pub fn file(repo: String, branch: String, path: String) -> Option<(File, Option<String>, Vec<u8>)> {
    if branch.contains(":") {
        return None;
    }
    let mut repo_path = CONFIG.git_location.clone();
    repo_path.push(format!("{}.git", repo));
    let repo = git2::Repository::open(repo_path).ok()?;
    let obj = repo.revparse_single(&format!("{}:{}", branch, path)).ok()?;
    match obj.kind() {
        Some(ObjectType::Blob) => {
            let blob = obj.as_blob()?;
            let mut path_to_folder = PathBuf::from(path);
            path_to_folder.pop();
            let path_to_folder = path_to_folder.into_os_string().to_str()?.to_string();
            let tree = repo
                .revparse_single(&format!("{}:{}", branch, path_to_folder))
                .ok()?;
            let tree = tree.as_tree()?;
            let tree_item = tree.get_id(blob.id())?;
            let file = File {
                name: tree_item.name()?.to_string(),
                size: Some(format_size(blob.size(), DECIMAL)),
                file_type: FileType::blob,
                properties: unix_mode::to_string(tree_item.filemode() as u32),
                properties_int: tree_item.filemode(),
            };
            let content = match blob.is_binary() {
                false => Some(String::from_utf8_lossy(blob.content()).into_owned()),
                true => None,
            };
            return Some((file, content, blob.content().iter().map(|x| *x).collect()));
        }
        _ => {
            return None;
        }
    }
}

#[derive(Serialize)]
pub struct File {
    pub name: String,
    pub size: Option<String>,
    pub file_type: FileType,
    pub properties: String,
    pub properties_int: i32,
}

#[derive(Serialize)]
pub enum FileType {
    blob,
    tree,
}