Browse Source

Merge branch 'master' of https://github.com/jrtechs/github-graphs

pull/11/head
CetaceanNation 5 years ago
parent
commit
89a56dc704
8 changed files with 471 additions and 13 deletions
  1. +0
    -1
      public/FriendsGraph.html
  2. +2
    -2
      public/GraphGenerator.html
  3. +84
    -0
      public/OrgRepoGraph.html
  4. +13
    -4
      public/about.html
  5. +336
    -0
      public/js/createOrgRepoGraph.js
  6. +2
    -2
      public/js/friendsGraph.js
  7. +32
    -1
      public/js/githubAPI.js
  8. +2
    -3
      public/js/profileGen.js

+ 0
- 1
public/FriendsGraph.html View File

@ -70,7 +70,6 @@
options.height = "700px";
createFriendsGraph(username, "myGraph", "graphLoading");
profileGen(username, "profileGen");
$("#searchBarTop").html("");
}
if(findGetParameter("name") !== null)

+ 2
- 2
public/GraphGenerator.html View File

@ -110,7 +110,7 @@
Creates a web chart of the specified organization
and all associated repos.
</p>
<button class="btn btn-outline-success rounder" onclick='toOrganization()' type='button'>Generate</button>
<button class="btn btn-outline-success rounder" onclick='toOrgRepos()' type='button'>Generate</button>
</div>
<p></p>
</div>
@ -145,5 +145,5 @@
var oname = fetchOrgInput();
window.location.href = "./OrgRepoGraph.html?name=" + oname;
}
</script>

+ 84
- 0
public/OrgRepoGraph.html View File

@ -0,0 +1,84 @@
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
<link rel="icon" href="./favicon.ico" type="image/x-icon" />
<link rel="shortcut icon" href="./favicon.ico" type="image/x-icon" />
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/css/bootstrap.min.css" integrity="sha384-ggOyR0iXCbMQv3Xipma34MD+dH/1fQ784/j6cY/iJTQUOhcWr7x9JvoRxT2MZw1T" crossorigin="anonymous">
<link rel="stylesheet" href="./style.css" />
<script
src="https://code.jquery.com/jquery-3.3.1.min.js"
integrity="sha256-FgpCb/KJQlLNfOu91ta32o/NMZxltwRo8QtmkMRdAu8="
crossorigin="anonymous">
</script>
<script src="js/githubAPI.js"></script>
<script src="js/createOrgRepoGraph.js"></script>
<script src="js/utilities.js"></script>
<script type="text/javascript" src="js/vis/vis.js"></script>
<link href="js/vis/vis-network.min.css" rel="stylesheet" type="text/css" />
</head>
<body>
<div id="header-bar" class="d-flex flex-column flex-md-row shadow-sm align-items-center">
<div id="header-title">
<a href="./index.html">
<img id="logo" src="./logo.svg" />
</a>
</div>
<div id="navigation">
<ul class="nav">
<li class="nav-item">
<a href="./GraphGenerator.html">
Generate graphs
</a>
</li>
<div class="nav-sep"></div>
<li class="nav-item">
<a href="https://github.com/jrtechs/github-graphs">
View on GitHub
</a>
</li>
<div class="nav-sep"></div>
<li class="nav-item">
<a href="./about.html">
About
</a>
</li>
</ul>
</div>
</div>
<div class="main container">
<div class="row">
<div class="col-md-8 col-12">
<h2 id="graphLabel"></h2>
<div id="myGraph" class="w-100"></div>
<pre id="eventSpan"></pre>
</div>
<div class="col-md-4 col-12 w-100">
<div id="profileGen"></div>
</div>
</div>
<script>
function createGraphs(orgname) {
options.width = $("#myGraph").width() + "px";
options.height = "700px";
createOrgRepoGraph(orgname, "myGraph", "graphLoading");
//orgRepoGen(orgname, "orgRepoGen");
}
if(findGetParameter("name") !== null) {
createGraphs(findGetParameter("name"))
}
</script>
</div>
</body>
</html>

+ 13
- 4
public/about.html View File

@ -46,7 +46,14 @@
</div>
<div id="content-body" class="container">
<p style="padding: 10px;">
jeff this is where you can write a bunch about the project
This is an interactive website which allows you to make graphs of the github network.
Currently we have three types of graphs-- the most popular of which is our friends graph.
The friends graphs helps you visualize clusters of friends/collaborators on GitHub.
This can be used to spot clusters within organizations and schools.
</p>
<p style="padding: 10px;">
This is an open source project, all the source code can be found on github.
New collaborators are always welcomed; look at our github repository for contributing guidelines.
</p>
</div>
<div id="content-title">
@ -55,6 +62,8 @@
<div id="content-body" class="container">
<p style="padding: 10px;">
This project was completed in 24 hours for participation in <a class="plink" href="https://brickhack.io/">BrickHack V</a> at the Rochester Institute of Technology.
We hope that this project will make people more interested in learning about big data analytics.
The visual aspect of this website makes learning about topics such as clustering and graph databases more intuitive.
</p>
</div>
<div id="content-title" style="border-radius: 20px;">
@ -68,7 +77,7 @@
</div>
<div class="card-body">
<p>
did stuff
I did a large chunk of work with the backend pulling data from github and generating the graphs with visJS.
</p>
</div>
<div class="links row text-center">
@ -96,7 +105,7 @@
</div>
<div class="card-body">
<p>
also did stuff
Worked on pulling api data from github to create the mini profile display and some graphs.
</p>
</div>
<div class="links row text-center">
@ -124,7 +133,7 @@
</div>
<div class="card-body">
<p>
kinda did stuff
Worked on the front end design of the website and designed graphic art for this website.
</p>
</div>
<div class="links row text-center">

+ 336
- 0
public/js/createOrgRepoGraph.js View File

@ -0,0 +1,336 @@
var nodes;
var edges;
var options = {
nodes: {
borderWidth:4,
size:30,
color: {
border: '#222222',
background: '#666666'
},
font:{color:'#eeeeee'}
},
edges: {
color: 'lightgray'
}
};
/**
* Checks if a user is a node in the graph
*
* @param userID
* @returns {boolean}
*/
function alreadyInGraph(userID)
{
for(var i = 0; i < nodes.length; i++)
{
if(nodes[i].id === userID)
{
return true;
}
}
return false;
}
/**
* adds a person to the nodes list
*
* @param profileData
*/
function addSelfAsOrg(orgData) {
nodes.push( {
id:orgData.id,
name:orgData.login,
image:orgData.avatar_url
});
}
function addSelfAsRepo(repoData) {
nodes.push( {
id:repoData.id,
name:repoData.name,
image:repoData.avatar_url
});
console.log(repoData.name);
}
/**
* Adds the followers/following of a person
* to the graph
*
* @param username
* @param apiPath
* @returns {Promise<any>}
*/
function addRepos(orgName, apiPath, page)
{
console.log(orgName + " page=" + page);
updateProgress();
return new Promise(function(resolve, reject) {
queryAPIByOrg(apiPath + "?page=" + page, orgName, function(data) {
console.log(data);
console.log(data.length);
var prom = [];
for(var i = 0; i < data.length; i++) {
if(!alreadyInGraph(data[i].id)) {
prom.push(addRepoToGraph(data[i]));
}
}
Promise.all(prom).then( () => {
if(data.length === 30) {
addRepos(orgName, apiPath, page+ 1).then(function() {
resolve();
})
}
else {
resolve();
}
})
},
function(error) {
reject(error);
})
});
}
/**
* Greedy function which checks to see if a edge is in the graphs
*
* @param id1
* @param id2
* @returns {boolean}
*/
function edgeInGraph(id1, id2)
{
console.log("edge check");
for(var i = 0;i < edges.length; i++)
{
if(edges[i].from === id1 && edges[i].to === id2)
{
return true;
}
if(edges[i].to === id1 && edges[i].from === id2)
{
return true;
}
}
return false;
}
/**
* Adds a connection to the graph
*
* @param person1
* @param person2
*/
function addConnection(person1, person2)
{
if(person1.id !== person2.id)
{
if(alreadyInGraph(person2.id) && !edgeInGraph(person1.id, person2.id))
{
edges.push(
{
from: person1.id,
to: person2.id
});
}
}
}
function processConnections(user, apiPoint, page)
{
updateProgress();
return new Promise(function(resolve, reject)
{
queryAPIByUser(apiPoint + "?page=" + page, user.name,
function(data)
{
for(var i = 0; i < data.length; i++)
{
addConnection(user, data[i])
}
if(data.length === 30)
{
processConnections(user, apiPoint, page + 1).then(function()
{
resolve();
});
}
else
{
resolve();
}
}, function(error)
{
console.log(error);
resolve();
})
})
}
/**
* Processes all the connections of a user and adds them to the graph
*
* @param user has .id and .name
* @returns {Promise<any>}
*/
function processUserConnections(user)
{
return new Promise(function(resolve, reject)
{
processConnections(user, API_FOLLOWING, 1).then(function()
{
processConnections(user, API_FOLLOWERS, 1).then(function()
{
resolve();
})
})
});
}
/**
* Creates connections between all the nodes in
* the graph.
*
* @returns {Promise<any>}
*/
function createConnections()
{
return new Promise(function(resolve, reject)
{
var prom = [];
for(var i = 0; i < nodes.length; i++)
{
prom.push(processUserConnections(nodes[i]));
}
Promise.all(prom).then(function()
{
resolve();
}).catch(function(error)
{
console.log(error);
resolve();
});
});
}
var total = 1;
var indexed = 0;
var progressID;
function updateProgress()
{
indexed++;
var percent = parseInt((indexed/total)*100);
$("#" + progressID).html("<div class=\"progress\">\n" +
" <div class=\"progress-bar progress-bar-striped progress-bar-animated\" role=\"progressbar\" style=\"width: " + percent + "%\" aria-valuenow=\"" + percent + "\" aria-valuemin=\"0\" aria-valuemax=\"100\"></div>\n" +
"</div>");
console.log();
}
/**
* Adds the base person to the graph.
*
* @param username
* @returns {Promise<any>}
*/
function addOrgToGraph(orgname) {
return new Promise(function(resolve, reject) {
queryAPIByOrg("", orgname, function(data) {
total = (data.public_repos) * 2;
addSelfAsOrg(data);
resolve();
},
function(error) {
reject(error);
});
});
}
function addRepoToGraph(repo) {
return new Promise(function(resolve, reject) {
console.log("in repo");
console.log(repo);
addSelfAsRepo(repo);
resolve();
/*
queryAPIByRepo(repo.name, orgname, function(data) {
//total = (data.followers + data.following) * 2;
addSelfAsRepo(data);
resolve();
console.log("did it");
},
function(error) {
reject(error);
});*/
});
}
function bringUpProfileView(id)
{
for(var i = 0; i < nodes.length; i++)
{
if(nodes[i].id === id) {
profileGen(nodes[i].name, "profileGen");
}
}
}
/**
* Creates a graph
* @param username
* @param containerName
* @param graphsTitle
*/
function createOrgRepoGraph(orgname, containerName, graphsTitle)
{
progressID = graphsTitle;
nodes = [];
edges = [];
addOrgToGraph(orgname).then(function() {
addRepos(orgname, API_REPOS,1).then(function() {
$("#" + progressID).html("");
var container = document.getElementById(containerName);
var data = {
nodes: nodes,
edges: edges
};
var network = new vis.Network(container, data, options);
network.on("click", function (params) {
params.event = "[original event]";
if(Number(this.getNodeAt(params.pointer.DOM)) !== NaN) {
bringUpProfileView(Number(this.getNodeAt(params.pointer.DOM)));
}
});
})
}).catch(function(error) {
alert("Invalid Organization");
});
}

+ 2
- 2
public/js/friendsGraph.js View File

@ -291,9 +291,9 @@ function bringUpProfileView(id)
* @param containerName
* @param graphsTitle
*/
function createFriendsGraph(username, containerName, graphsProgres)
function createFriendsGraph(username, containerName, graphsTitle)
{
progressID = graphsProgres;
progressID = graphsTitle;
nodes = [];
edges = [];

+ 32
- 1
public/js/githubAPI.js View File

@ -11,6 +11,10 @@ const APIROOT = "api";
const API_USER_PATH = "/users/";
const API_ORG_PATH = "/orgs/";
const API_REPOS = "/repos/";
const API_FOLLOWING = "/following";
const API_FOLLOWERS = "/followers";
@ -42,4 +46,31 @@ function queryAPIByUser(apiPath, user, successCallBack, errorCallBack) {
error:errorCallBack,
timeout: 4000
});
}
}
function queryAPIByOrg(apiPath, org, successCallBack, errorCallBack) {
const urlpath = APIROOT + API_ORG_PATH + org + apiPath;
$.ajax({
type:'GET',
url: urlpath,
crossDomain: true,
dataType: "json",
success: successCallBack,
error:errorCallBack,
timeout: 4000
});
console.log("past");
}
/*
function queryAPIByRepo(apiPath, org, successCallBack, errorCallBack) {
const urlpath = APIROOT + API_ORG_PATH + org + apiPath;
$.ajax({
type:'GET',
url: urlpath,
crossDomain: true,
dataType: "json",
success: successCallBack,
error:errorCallBack,
timeout: 4000
});
}*/

+ 2
- 3
public/js/profileGen.js View File

@ -45,7 +45,7 @@ function profileGen(username, container)
(user.company != null ? "<li class=\"list-group-item\">Company: "+user.company+"</li>" : "")+
(orgsReturn != [] ? "<li class=\"list-group-item\">"+orgsReturn+"</li>" : "")+ " \
</ul> \
</div>"
</div>";
$("#"+container).html(html);
})
}, () => {
@ -79,8 +79,7 @@ function parseOrgs(name) {
resolve(orgs_final.join(" "));
})
}, (error) => {
console.error("error getting orgs");
reject(error);
resolve([]);
});
})
}

Loading…
Cancel
Save