~/selfhut

b1605a548f87ae1f470663737996fc16bdd77dba — Arthur Melton 614876c0 2 years ago
refs
A src/git/branches.rs +35 -0
@@ 0,0 1,35 @@

use crate::config::CONFIG;
use crate::git::commits::{Commits, get_commits};
use serde_derive::Serialize;

pub fn branches(repo_name: String) -> Option<Vec<Branch>> {
    let mut repo_path = CONFIG.git_location.clone();
    repo_path.push(format!("{}.git", repo_name));
    let repo = git2::Repository::open(repo_path).ok()?;
    let mut branches = Vec::new();
    for i in repo.branches(Some(git2::BranchType::Local)).ok()? {
        match i {
            Ok(x) => match x.0.name() {
                Ok(name) => match name {
                        Some(name) => branches.push(Branch {
                            branch: name.to_string(),
                            commit: match get_commits(repo_name.clone(), 1, Some(name.to_string()), None) {
                                Some(x) => x.first().cloned(),
                                None => None
                            },
                        }),
                        None => {}
                    }
                Err(_) => {}
            },
            Err(_) => {}
        }
    }
    Some(branches)
}

#[derive(Serialize, Clone)]
pub struct Branch {
    branch: String,
    commit: Option<Commits>
}

M src/git/commits.rs => src/git/commits.rs +24 -1
@@ 17,7 17,30 @@ pub fn get_commits(


    revwalk.set_sorting(git2::Sort::TIME).ok()?;
    match after {
        Some(id) => revwalk.push(git2::Oid::from_str(id.as_str()).ok()?).ok()?,
        Some(id) => match git2::Oid::from_str(id.as_str()) {
            Ok(x) => revwalk.push(x).ok()?,
            Err(_) => {
                let oid = match repo.find_branch(&id, git2::BranchType::Local) {
                    Ok(x) => x.get().target(),
                    Err(_) => {
                        let mut tag = None;
                        let tag_name = id.as_bytes();
                        repo.tag_foreach(|x,y| {
                            if &y[10..] == tag_name {
                                tag = Some(x);
                                return false;
                            }
                            true
                        });
                        tag
                    }
                };
                match oid {
                    Some(x) => revwalk.push(x).ok()?,
                    None => revwalk.push_head().ok()?
                }
            }
        }
        None => revwalk.push_head().ok()?,
    }
    let mut commits = Vec::new();

M src/git/mod.rs => src/git/mod.rs +1 -0
@@ 5,3 5,4 @@ pub mod file;

pub mod main_branch;
pub mod repos;
pub mod tag;
pub mod branches;

M src/git/tag.rs => src/git/tag.rs +39 -11
@@ 1,18 1,46 @@

use crate::config::CONFIG;
use crate::git::commits::{get_commits, Commits};
use serde_derive::Serialize;

pub fn get_tag(repo_name: String, amount: usize) -> Option<Vec<String>> {
pub fn get_tag(repo_name: String, amount: usize, after: usize, name: Option<String>) -> Option<(Vec<Tags>, usize)> {
    let mut repo_path = CONFIG.git_location.clone();
    repo_path.push(format!("{}.git", repo_name));
    let repo = git2::Repository::open(repo_path).ok()?;
    let mut tags = Vec::new();
    let mut i = 0;
    let repo_tags = repo.tag_names(None).ok()?;
    let mut tags_stringarray = repo_tags.iter().rev();
    let mut tag = tags_stringarray.next();
    while i < amount && tag.is_some() && tag.unwrap().is_some() {
        tags.push(tag.unwrap().unwrap().to_string());
        tag = tags_stringarray.next();
        i += 1;
    }
    Some(tags)
    let total = repo.tag_names(None).ok()?.len();
    let mut i = total-1;
    repo.tag_foreach(|x,y| {
        if (name.is_some() && name.as_ref().unwrap().as_bytes() == &y[10..]) || name.is_none() {
            if i >= after && (total < amount + after ||  i < amount - after) {
                match get_commits(repo_name.clone(), 1, Some(x.to_string()), None) {
                    Some(z) => match z.first() {
                        Some(z) => tags.push(Tags {
                            commit: z.clone(),
                            body: match repo.find_tag(x) {
                                Ok(x) => x.message().unwrap_or("").to_string(),
                                Err(_) => "".to_string()
                            },
                            name: std::str::from_utf8(&y[10..]).unwrap_or("").to_string()
                        }),
                        None => {}
                    },
                    None => {}
                }
            }
            if i < after+1 {
                return false;
            }
            i-=1;
        }
        true
    });
    tags.reverse();
    Some((tags, total))
}

#[derive(Serialize, Clone)]
pub struct Tags {
    commit: Commits,
    name: String,
    body: String,
}

M src/main.rs => src/main.rs +4 -1
@@ 17,6 17,7 @@ use crate::repository::log;

use crate::repository::raw;
use crate::repository::summary;
use crate::repository::tree;
use crate::repository::refs;
use crate::utils::own_pathbuf::PathBufWithDotfiles;
use rocket_dyn_templates::Template;


@@ 38,7 39,9 @@ fn rocket() -> _ {

                log::log,
                blame::blames,
                commit::commit,
                commit::patch
                commit::patch,
                refs::refs,
                refs::refs_id
            ],
        )
        .attach(Template::fairing())

M src/repository/blame.rs => src/repository/blame.rs +1 -1
@@ 51,7 51,7 @@ pub fn blames(repo: String, branch: String, location: PathBufWithDotfiles) -> Op

            config: repo_config(repo.clone()),
            domain: CONFIG.domain.to_string(),
            active: "tree",
            commit: match get_commits(repo.clone(), 1, None, Some(format!("{}", location.get().display()).replace("//", "/"))) {
            commit: match get_commits(repo.clone(), 1, Some(branch.clone()), Some(format!("{}", location.get().display()).replace("//", "/"))) {
                Some(x) => match x.clone().get(0) {
                    Some(x) => Some(x.clone()),
                    None => None

M src/repository/log.rs => src/repository/log.rs +1 -1
@@ 58,7 58,7 @@ pub fn log(

    let commits = get_commits(
        repo.clone(),
        21,
        from,
        Some(from.unwrap_or(branch.clone())),
        Some(format!("{}", location.get().display()).replace("//", "/")),
    );
    let last_commit = match commits {

M src/repository/mod.rs => src/repository/mod.rs +1 -0
@@ 4,3 4,4 @@ pub mod log;

pub mod raw;
pub mod summary;
pub mod tree;
pub mod refs;

A src/repository/refs.rs +65 -0
@@ 0,0 1,65 @@

use crate::config::CONFIG;
use crate::git::branches::branches;

use crate::git::main_branch::main_branch;
use crate::git::tag::get_tag;
use crate::utils::repo_config::repo_config;
use rocket_dyn_templates::{context, Template};

#[get("/<repo>/refs?<page>", rank = 2)]
pub fn refs(repo: String, page: Option<usize>) -> Option<Template> {
    let mut tags = get_tag(repo.clone(), 11, (page.unwrap_or(1)-1)*10, None);
    let mut pages = 1;
    let mut forward = false;
    match tags {
        Some(ref mut x) => {
                pages = x.1/10+1;
                if x.0.len() == 11 {
                    forward = true;
                    x.0.pop();
                }
            },
        None => {}
    }
    Some(Template::render(
        "repository/refs",
        context! {
            title: format!("/ :: {}", repo.clone()),
            repo: repo.clone(),
            config: repo_config(repo.clone()),
            domain: CONFIG.domain.to_string(),
            active: "refs",
            current_dir_file: "/",
            current_dir: "/",
            payment: CONFIG.payment_link.clone(),
            mailing_list: CONFIG.mailing_list.clone(),
            branch: branches(repo.clone()),
            tag: tags,
            page_dec: page.unwrap_or(1)-1,
            page_inc: page.unwrap_or(1)+1,
            total_page: pages,
            page: page.unwrap_or(1)
        },
    ))
}

#[get("/<repo>/refs/<name>", rank = 2)]
pub fn refs_id(repo: String, name: String) -> Option<Template> {
    let binding = get_tag(repo.clone(), 1, 0, Some(name))?;
    let tag = binding.0.first()?;
    Some(Template::render(
        "repository/ref",
        context! {
            title: format!("/ :: {}", repo.clone()),
            repo: repo.clone(),
            config: repo_config(repo.clone()),
            domain: CONFIG.domain.to_string(),
            active: "refs",
            current_dir_file: "/",
            current_dir: "/",
            payment: CONFIG.payment_link.clone(),
            mailing_list: CONFIG.mailing_list.clone(),
            tag: tag,
        },
    ))
}

M src/repository/summary.rs => src/repository/summary.rs +2 -2
@@ 23,8 23,8 @@ pub fn repository(repo: String) -> Option<Template> {

            active: "summary",
            preview: get_commits(repo.clone(), 3, None, None),
            main_branch,
            tag: match get_tag(repo.clone(), 1) {
                Some(x) => match x.get(0) {
            tag: match get_tag(repo.clone(), 1, 0, None) {
                Some(x) => match x.0.get(0) {
                    Some(x) => Some(x.clone()),
                    None => None
                },

M src/repository/tree.rs => src/repository/tree.rs +2 -2
@@ 77,7 77,7 @@ pub fn tree(repo: String, branch: String, location: PathBufWithDotfiles) -> Opti

                    config: repo_config(repo.clone()),
                    domain: CONFIG.domain.to_string(),
                    active: "tree",
                    commit: match get_commits(repo.clone(), 1, None, Some(format!("{}", location.get().display()).replace("//", "/"))) {
                    commit: match get_commits(repo.clone(), 1, Some(branch.clone()), Some(format!("{}", location.get().display()).replace("//", "/"))) {
                        Some(x) => match x.clone().get(0) {
                            Some(x) => Some(x.clone()),
                            None => None

@@ 104,7 104,7 @@ pub fn tree(repo: String, branch: String, location: PathBufWithDotfiles) -> Opti

                config: repo_config(repo.clone()),
                domain: CONFIG.domain.to_string(),
                active: "tree",
                commit: match get_commits(repo.clone(), 1, None, Some(format!("{}", location.get().display()).replace("//", "/"))) {
                commit: match get_commits(repo.clone(), 1, Some(branch.clone()), Some(format!("{}", location.get().display()).replace("//", "/"))) {
                    Some(x) => match x.clone().get(0) {
                        Some(x) => Some(x.clone()),
                        None => None

A templates/repository/ref.html.hbs +28 -0
@@ 0,0 1,28 @@

{{#*inline "page"}}
{{> navbar}}
<div class="container">
    <h3>{{tag.name}}
        <small class="pull-right text-muted">
            <span title="{{tag.commit.time_utc}}">{{tag.commit.time_relitive}}</span>
        </small>
    </h3>
    <div class="row">
        <div class="col-md-4">
            <div class="form-group">
                <a class="btn btn-primary btn-block" href="/{{repo}}/archive/{{tag.name}}.tar.gz">.tar.gz <span aria-hidden="true" class="icon icon-caret-right"><svg viewBox="0 0 192 512" xmlns="http://www.w3.org/2000/svg"><path d="M0 384.662V127.338c0-17.818 21.543-26.741 34.142-14.142l128.662 128.662c7.81 7.81 7.81 20.474 0 28.284L34.142 398.804C21.543 411.404 0 402.48 0 384.662z"></path></svg>
                </span></a>
                <a class="btn btn-default btn-block" href="/{{repo}}/tree/{{tag.name}}">browse <span aria-hidden="true" class="icon icon-caret-right"><svg viewBox="0 0 192 512" xmlns="http://www.w3.org/2000/svg"><path d="M0 384.662V127.338c0-17.818 21.543-26.741 34.142-14.142l128.662 128.662c7.81 7.81 7.81 20.474 0 28.284L34.142 398.804C21.543 411.404 0 402.48 0 384.662z"></path></svg>
                </span></a>
            </div>
        </div>
        <div class="col-md-8">
            <div class="event-list">
                    <div class="event">
                    <pre style="padding-bottom: 0;">{{tag.body}}</pre>
                </div>
            </div>
        </div>
    </div>
</div>
{{/inline}}
{{> layout}}

A templates/repository/refs.html.hbs +83 -0
@@ 0,0 1,83 @@

{{#*inline "page"}}
{{> navbar}}
<div class="container">
	<div class="row" style="margin-bottom: 1rem">
		<div class="col-md-8">
            {{#each tag.0}}
            <div class="event">
            <h4 style="margin-bottom: 0.5rem">
                <a href="/{{../repo}}/refs/{{this.name}}">
                    {{this.name}}
                </a>
                <small class="pull-right text-muted">
                    <span title="{{this.commit.time_utc}}">{{this.commit.time_relitive}}</span>
                    <a href="/{{../repo}}/archive/{{this.name}}.tar.gz" rel="nofollow" style="margin-left: 0.5rem">.tar.gz <span aria-hidden="true" class="icon icon-caret-right"><svg viewBox="0 0 192 512" xmlns="http://www.w3.org/2000/svg"><path d="M0 384.662V127.338c0-17.818 21.543-26.741 34.142-14.142l128.662 128.662c7.81 7.81 7.81 20.474 0 28.284L34.142 398.804C21.543 411.404 0 402.48 0 384.662z"></path></svg>
                    </span></a>
                    <a href="/{{../repo}}/tree/{{this.name}}" style="margin-left: 0.5rem">browse <span aria-hidden="true" class="icon icon-caret-right"><svg viewBox="0 0 192 512" xmlns="http://www.w3.org/2000/svg"><path d="M0 384.662V127.338c0-17.818 21.543-26.741 34.142-14.142l128.662 128.662c7.81 7.81 7.81 20.474 0 28.284L34.142 398.804C21.543 411.404 0 402.48 0 384.662z"></path></svg>
                    </span></a>
                    <a href="/{{../repo}}/log/{{this.name}}" style="margin-left: 0.5rem">log <span aria-hidden="true" class="icon icon-caret-right"><svg viewBox="0 0 192 512" xmlns="http://www.w3.org/2000/svg"><path d="M0 384.662V127.338c0-17.818 21.543-26.741 34.142-14.142l128.662 128.662c7.81 7.81 7.81 20.474 0 28.284L34.142 398.804C21.543 411.404 0 402.48 0 384.662z"></path></svg>
                    </span></a>
                </small>
            </h4>
            <pre style="padding-bottom: 0;">{{this.body}}</pre>
</div>            
            {{/each}}
			{{#if (ne total_page 1)}}
			<div class="row">
				<div class="col-4">
					{{#if (ne page 1)}}
					<a class="btn btn-default" href="?page={{page_dec}}">
						<span aria-hidden="true" class="icon icon-caret-left">
							<svg viewBox="0 0 192 512" xmlns="http://www.w3.org/2000/svg">
								<path d="M192 127.338v257.324c0 17.818-21.543 26.741-34.142 14.142L29.196 270.142c-7.81-7.81-7.81-20.474 0-28.284l128.662-128.662c12.599-12.6 34.142-3.676 34.142 14.142z"></path>
							</svg>
						</span>
						prev
					</a>
					{{/if}}
				</div>
				<div class="col-4 text-centered">
					{{page}} / {{ total_page }}
				</div>
				{{#if (ne page total_page)}}
				<div class="col-4 text-right">
					<a class="btn btn-default" href="?page={{page_inc}}">
						next
						<span aria-hidden="true" class="icon icon-caret-right">
							<svg viewBox="0 0 192 512" xmlns="http://www.w3.org/2000/svg">
								<path d="M0 384.662V127.338c0-17.818 21.543-26.741 34.142-14.142l128.662 128.662c7.81 7.81 7.81 20.474 0 28.284L34.142 398.804C21.543 411.404 0 402.48 0 384.662z"></path>
							</svg>
						</span>
					</a>
				</div>
				{{/if}}
			</div>
			{{/if}}
        </div>
		<div class="col-md-4">
            <h3>Branches</h3>
            <div class="event-list">
                {{#each branch}}
                <div class="event">{{this.branch}}
                    <div>
                        <a href="/{{../repo}}/commit/{{this.commit.commit_hash}}" title="{{this.commit.commit_hash}}">{{this.commit.commit_hash_short}}</a> — {{this.commit.commitie}}
                        <small class="pull-right">
                            <a href="/{{../repo}}/log?from={{this.commit.commit_hash}}#log-{{this.commit.commit_hash}}" id="log-{{this.commit_hash}}"><span title="{{this.commit.time_utc}}">{{this.commit.time_relitive}}</span></a>
                        </small>
                    </div>
                    <div class="row" style="margin-top: 0.5rem">
                        <div class="col">
                            <a class="btn btn-block btn-primary" href="/{{../repo}}/tree/{{this.branch}}">browse <span aria-hidden="true" class="icon icon-caret-right"><svg viewBox="0 0 192 512" xmlns="http://www.w3.org/2000/svg"><path d="M0 384.662V127.338c0-17.818 21.543-26.741 34.142-14.142l128.662 128.662c7.81 7.81 7.81 20.474 0 28.284L34.142 398.804C21.543 411.404 0 402.48 0 384.662z"></path></svg></span></a>
                        </div>
                        <div class="col">
                            <a class="btn btn-block btn-default" href="/{{../repo}}/log/{{this.branch}}">log <span aria-hidden="true" class="icon icon-caret-right"><svg viewBox="0 0 192 512" xmlns="http://www.w3.org/2000/svg"><path d="M0 384.662V127.338c0-17.818 21.543-26.741 34.142-14.142l128.662 128.662c7.81 7.81 7.81 20.474 0 28.284L34.142 398.804C21.543 411.404 0 402.48 0 384.662z"></path></svg></span></a>
                        </div>
                    </div>
                </div>
                {{/each}}
            </div>
        </div>
	</div>
</div>
{{/inline}}
{{> layout}}

M templates/repository/summary.html.hbs => templates/repository/summary.html.hbs +2 -2
@@ 52,7 52,7 @@

						{{#if tag}}
						<dt>ref</dt>
						<dd>
							<a href="/{{repo}}/refs/{{tag}}">
							<a href="/{{repo}}/refs/{{tag.name}}">
								release notes&nbsp;
								<span aria-hidden="true" class="icon icon-caret-right">
									<svg viewBox="0 0 192 512" xmlns="http://www.w3.org/2000/svg">

@@ 82,4 82,4 @@

	</div>
</div>
{{/inline}}
{{> layout}}
\ No newline at end of file
{{> layout}}