Skip to content

Commit

Permalink
better git pull. and trigger bubble updates
Browse files Browse the repository at this point in the history
  • Loading branch information
ebuchman committed Aug 21, 2014
1 parent 1c01db8 commit dc278e2
Show file tree
Hide file tree
Showing 6 changed files with 153 additions and 32 deletions.
5 changes: 4 additions & 1 deletion cmd/bloke/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,10 @@ func main(){

flag.Parse()

SiteRoot := "."
SiteRoot, err := os.Getwd()
if err !=nil{
log.Fatal("could not get site root", err)
}

if *InitSite != ""{
bloke.CreateNewSite(*InitSite)
Expand Down
13 changes: 10 additions & 3 deletions init.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,12 @@ type ConfigType struct{
// load config struct from config.json
func (g * Globals) LoadConfig(SiteRoot string){
g.SiteRoot = SiteRoot
log.Println("site root from config", g.SiteRoot)
wd, err := os.Getwd()
if err != nil{
log.Fatal("shit tits")
}
log.Println("working dir:", wd)
file, e := ioutil.ReadFile(path.Join(g.SiteRoot, "config.json"))
if e != nil{
log.Fatal("no config", e)
Expand All @@ -39,8 +45,6 @@ func (g * Globals) LoadConfig(SiteRoot string){
json.Unmarshal(file, &c)
g.Config = c

g.Close = make(chan bool)

// sync with git repo first time
if g.Config.Repo != ""{
log.Println("Iniitializing git repo and syncing with github remote", g.Config.Repo)
Expand Down Expand Up @@ -102,12 +106,15 @@ func (g *Globals) LoadSecret(){
g.webhookSecret = b
}

func GetTemplates(root string) *template.Template{
return template.Must(template.ParseFiles(root+"/views/page.html", root+"/views/nav.html", root+"/views/footer.html", root+"/views/bubbles.html", root+"/views/header.html"))
}
// main server startup function
// compile lists of pages and posts and prepare globals struct
// require at least one page and one post!
func (g *Globals) AssembleSite(){
// render templates
g.Templates = template.Must(template.ParseFiles(g.SiteRoot+"/views/page.html", g.SiteRoot+"/views/nav.html", g.SiteRoot+"/views/footer.html", g.SiteRoot+"/views/bubbles.html", g.SiteRoot+"/views/header.html"))
g.Templates = GetTemplates(g.SiteRoot)
// go through pages and posts and entries
g.AssemblePages()
g.AssemblePosts()
Expand Down
22 changes: 11 additions & 11 deletions pages.go
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ type MetaInfoType struct {
}

// info specific to the page requested by a client
type pageType struct{
type PageType struct{
Name string //URL name of this page
Text string // text of current page
Title string // title of current page
Expand All @@ -32,7 +32,7 @@ type pageType struct{


// bring a template to life!
func (g *Globals) renderTemplate(w http.ResponseWriter, tmpl string, p interface{}){
func (g *Globals) RenderTemplate(w http.ResponseWriter, tmpl string, p interface{}){
//we already parsed the html templates
err := g.Templates.ExecuteTemplate(w, tmpl+".html", p)
if err != nil {
Expand All @@ -42,14 +42,14 @@ func (g *Globals) renderTemplate(w http.ResponseWriter, tmpl string, p interface

// error function
func (g *Globals) errorPage(w http.ResponseWriter, err error){
page := new(pageType)
page := new(PageType)
page.Title = "Error"
page.Text = err.Error()
g.renderTemplate(w, "page", viewType{Page: page, Globals: g})
g.RenderTemplate(w, "page", ViewType{Page: page, Globals: g})
}

// load and parse a page and relevent metainfo
func (g *Globals) LoadPage(dirPath, name string, page *pageType) error{
func (g *Globals) LoadPage(dirPath, name string, page *PageType) error{
// read markdown file
// log.Println(path.Join(dirPath, name+".md"))
b, err := ioutil.ReadFile(path.Join(dirPath,name+".md"))
Expand Down Expand Up @@ -133,18 +133,18 @@ func (g *Globals) SaveSite(){
for _, p := range g.Projects{
name := p[0]
if _, ok := g.SubProjects[name]; !ok{
page := new(pageType)
page := new(PageType)
CheckFatal(g.LoadPage(path.Join(g.SiteRoot, "pages"), name, page))
g.RenderTemplateToFile("page", path.Join(g.SiteRoot, "_site", "pages"), name, viewType{page, g})
g.RenderTemplateToFile("page", path.Join(g.SiteRoot, "_site", "pages"), name, ViewType{page, g})
} else{
// deal with subprojects!
subprojs := g.SubProjects[name]
for _, sp := range subprojs{
sp_name := sp[0]
page := new(pageType)
page := new(PageType)
CheckFatal(os.MkdirAll(path.Join(g.SiteRoot, "_site", "pages", name), 0777))
CheckFatal(g.LoadPage(path.Join(g.SiteRoot, "pages", name), sp_name, page))
g.RenderTemplateToFile("page", path.Join(g.SiteRoot, "_site", "pages", name), sp_name, viewType{page, g})
g.RenderTemplateToFile("page", path.Join(g.SiteRoot, "_site", "pages", name), sp_name, ViewType{page, g})
}

}
Expand All @@ -157,9 +157,9 @@ func (g *Globals) SaveSite(){
for d, _ := range g.Posts[y][m]{
for _, t := range g.Posts[y][m][d]{
name := y+"-"+m+"-"+d+"-"+t
page := new(pageType)
page := new(PageType)
CheckFatal(g.LoadPage(path.Join(g.SiteRoot, "posts"), name, page))
g.RenderTemplateToFile("page", path.Join(g.SiteRoot, "_site", "posts"), name, viewType{page, g})
g.RenderTemplateToFile("page", path.Join(g.SiteRoot, "_site", "posts"), name, ViewType{page, g})
}
}
}
Expand Down
15 changes: 7 additions & 8 deletions routing.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,8 +15,8 @@ import (

// this guy gets passed to the go templates. simply has pointers to the globals and the page
// every request sees the same globals, but a different page
type viewType struct{
Page *pageType
type ViewType struct{
Page *PageType
Globals *Globals
}

Expand All @@ -29,10 +29,9 @@ type viewType struct{
/ProjectName/SubProjectName a particular subproject page
*/
func (g *Globals) handleIndex(w http.ResponseWriter, r *http.Request){
log.Println("handle Index", r.URL.Path)
log.Println("handle Index", r.Host)
log.Println("handle Index", r.URL.Path, r.Host)

page := new(pageType)
page := new(PageType)
// is URL is empty, serve main page, else validate URL and LoadPage
if len(r.URL.Path[1:]) > 0{
path_elements := strings.Split(r.URL.Path[1:], "/")
Expand Down Expand Up @@ -79,7 +78,7 @@ func (g *Globals) handleIndex(w http.ResponseWriter, r *http.Request){
return
}
}
g.renderTemplate(w, "page", viewType{Page:page, Globals:g})
g.RenderTemplate(w, "page", ViewType{Page:page, Globals:g})
}

type Bubble struct{
Expand Down Expand Up @@ -131,8 +130,8 @@ func (g *Globals) ajaxBubbleResponse(w http.ResponseWriter, r *http.Request){

func (g *Globals) ajaxPagesResponse(w http.ResponseWriter, r *http.Request){
split := strings.Split(r.URL.Path[1:], "/")
log.Println(split)
page := new(pageType)
log.Println("shit son", split)
page := new(PageType)
if len(split) > 1 && split[1] != ""{
err := g.LoadPage(g.SiteRoot, r.URL.Path[1:], page)
if err != nil{
Expand Down
50 changes: 42 additions & 8 deletions server.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ import (
)

/* TODO
- Glossary/bubbles page
- bubbles only display one line!
- better home/blog definition
- pdfs in bubbles?
- clean up js bubbles so they follow user as they scroll
Expand Down Expand Up @@ -41,14 +41,35 @@ type Globals struct{

Templates *template.Template

Close chan bool // close server channel

mux *http.ServeMux // when many blokes are run behind one serve, give each a routing mux (instead of standalone server)

UpdateHandler UpdateHandler // called with names of updated bubbles

html bool // whether to serve html pages from _sites/ or to generate on the fly
watch bool // whether to watch dir for changes
}

// for handling bubble updates
// this can be ignored, if the updates are in text files being served
// it can trigger database lookups/modifications
// it can do whatever else you want
// point is, separate bloke site generator from the bupble database
type UpdateHandler interface{
// takes a list of the names of the updated bubbles
HandleUpdate(map[string]int)
}

// not even using this. is bloke is running as a simple site generator, no one cares, this is nil
// if bloke is being hosted, you probably want to implement an UpdateHandler to talk to the db
type baseUpdateHandler struct{

}

func (b baseUpdateHandler) HandleUpdate(updates map[string]int){
log.Println("booya nigga")
log.Println(updates)
}

// new ServeMux.
func (g *Globals) NewServeMux(){
g.mux = http.NewServeMux()
Expand All @@ -61,7 +82,7 @@ func (g *Globals) ServeHTTP(w http.ResponseWriter, r *http.Request){
}

// launch a new live bloke
func LiveBloke(SitePath string, no_html bool) Globals{
func LiveBloke(SitePath string, no_html bool, update_handler UpdateHandler) Globals{
var g = Globals{}
g.html = !no_html // whether or not to serve html from _sites/
g.LoadConfig(SitePath) // load config
Expand All @@ -72,14 +93,26 @@ func LiveBloke(SitePath string, no_html bool) Globals{
if g.watch{
g.NewWatcher(SitePath) // watch the root directory
}
g.UpdateHandler = update_handler//baseUpdateHandler{}
g.NewServeMux() // creates g.mux and applies standard routing rules
return g
}

// create new globals, copy over (eg. after git pull)
func (g *Globals) Refresh(){
// takes a list of bubble names recently updates
func (g *Globals) Refresh(updates map[string]int){
// if nil, its coming from local watchdir callback, which is experimental
// and kind of shitty

// TODO: close all old g things!
*g = LiveBloke(g.SiteRoot, g.html)

// if a bubble is updated, we need to know!
log.Println(g.Config.SiteName, g.UpdateHandler)
if g.UpdateHandler != nil{
g.UpdateHandler.HandleUpdate(updates)
}

*g = LiveBloke(g.SiteRoot, g.html, g.UpdateHandler)
}

// serve static files (assets: js, css)
Expand Down Expand Up @@ -140,7 +173,7 @@ func (g *Globals) WatchDirCallback(watcher *fsnotify.Watcher){
split := strings.Split(ev.Name, "/")
name := split[len(split)-1]
if !strings.HasPrefix(name, ".") && !strings.HasSuffix(name, "~"){
g.Refresh()
g.Refresh(nil)
}
}
case err := <-watcher.Error:
Expand Down Expand Up @@ -209,6 +242,7 @@ func RedirectServer(){

// start a http or https server listening on addr routing with the mux
func StartServer(addr string, mux *http.ServeMux, tls bool){
log.Println("wtf!")
if tls{
_, err := ioutil.ReadDir("certs")
if err != nil{
Expand All @@ -228,7 +262,7 @@ func StartServer(addr string, mux *http.ServeMux, tls bool){

// standalone server for running your own bloke
func StartBloke(addr, SiteRoot string, tls bool, no_html bool) {
g := LiveBloke(SiteRoot, no_html)
g := LiveBloke(SiteRoot, no_html, nil)
StartServer(addr, g.mux, tls)
}

80 changes: 79 additions & 1 deletion util.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,16 +24,94 @@ func CheckMAC(message, messageMAC, key []byte) bool {
// if git pull not up to date, refresh Globals
// how do we pull safely, without messing up a user?!
func (g *Globals) GitPull(){
current, _ := os.Getwd()
os.Chdir(g.SiteRoot)

cmd := exec.Command("git", "pull", "origin", "master")
var out bytes.Buffer
cmd.Stdout = &out
cmd.Run()
log.Println(out.String())
// parse output for list of new/changed bubbles
updates := BubbleUpdates(out.String())
if !strings.Contains(out.String(), "already up-to-date"){
g.Refresh()
g.Refresh(updates)
}
os.Chdir(current)
}

func getNameFromPathSpace(head_dir, str string) string{
splitt := strings.Split(str, " ")
sb := ""
for _, s := range splitt{
if strings.Contains(s, head_dir){
sb = s
}
}
sp := strings.Split(sb, "/")
f := sp[len(sp)-1]
sp = strings.Split(f, ".")
return sp[0]
}

// check if changes introduce or change bubbles. return list of them
// for now it only works on changes, adds, and rms. Rename's mess it all up!
// redo with regex for christ's sake!
func BubbleUpdates(gitpull string) map[string]int{
updates := make(map[string]int)
split := strings.Split(gitpull, "\n")
log.Println("looking for bubble changes....")
var i int
var s string
for i, s = range split{
// this should be a regexp..
if strings.Contains(s, "file") && strings.Contains(s, "insertion") && strings.Contains(s, "deletion"){
log.Println("done checking changes")
break
}

// bubbles/filename.md | 12 +++
splitt := strings.Split(s, "|")
if len(split) != 2{
continue
}
name := splitt[0]
info := splitt[1]
// we only care about changes to bubbles
if strings.Contains(name, "bubbles/"){
// parse name to get the file name
name := getNameFromPathSpace("bubbles/", name)
log.Println("potential bubble", name)
// parse info to detect if this was a change or an add/rm
if strings.Contains(info, "+") || strings.Contains(info, "-"){
log.Println("a change!")
updates[name] = 0
}// if it was add/rm, it will have no +/-

} else {
continue
}
}
log.Println("done changes ya", i)
// at this point, we've seen all the changes, but those that were only add/rm we ignored. now we find out create/delete
for _, s:= range split[i:]{
log.Println(s)
if strings.Contains(s, " mode ") && strings.Contains(s, " bubbles/"){
name := getNameFromPathSpace("bubbles/", s)
log.Println("potential add/rm", name)
if strings.Contains(s, "delete mode "){
updates[name] = 1
} else if strings.Contains(s, "create mode "){
updates[name] = 2
}
log.Println("the upd", updates[name])
}
}

return updates
}


// check if given dir is a bloke
func IsBloke(pathname string) bool{
_, err := os.Stat(path.Join(pathname, ".isbloke"))
Expand Down

0 comments on commit dc278e2

Please sign in to comment.