Skip to content

Instantly share code, notes, and snippets.

@kondor6c
Created February 2, 2021 14:47
Show Gist options
  • Save kondor6c/f9c1d3aefd7a903c5e3036ac4253a323 to your computer and use it in GitHub Desktop.
Save kondor6c/f9c1d3aefd7a903c5e3036ac4253a323 to your computer and use it in GitHub Desktop.
// thrown together (yes, its ugly) by kevin faulkner, if you use/modify it or want help, let me know
// under some kind of BSD license, just note original author so that I can meet more people that like doing this Linux stuff :-)
package main
import (
"bytes"
"database/sql"
"encoding/json"
"log"
"net/http"
"os"
"regexp"
"runtime"
_ "github.com/mattn/go-sqlite3"
"github.com/slack-go/slack"
"github.com/slack-go/slack/slackevents"
)
type InstantMessage struct {
Id uint64 `json:"id"`
User string `json:"user"`
Type string `json:"type"`
Mechanism string `json:"mechanism"`
Channel string `json:"channel"`
Text string `json:"text"`
Reaction string `json:"reaction"`
}
var secret = os.Getenv("SECRET")
var sApi = slack.New(secret)
func Catcher(err error) {
if err != nil {
log.Println(err)
}
}
func (im *InstantMessage) action() {
}
func (im *InstantMessage) send() {
}
func dbInit(sqliteFile string) *sql.DB {
db, err := sql.Open("sqlite3", sqliteFile) //we tell the standard lib sql we want to use sqlite3 driver
Catcher(err) // I cringe now that I see I was discarding the error, this caused me issues
var idea_table = "CREATE TABLE IF NOT EXISTS inspiring_ideas (id INTEGER PRIMARY KEY, body TEXT, read_by_user TEXT, responses TEXT, tag TEXT, frequency INTEGER)"
var creates = []string{
"CREATE TABLE IF NOT EXISTS config (id INTEGER PRIMARY KEY, channel TEXT, protocol TEXT, tag TEXT, frequency INTEGER)",
"CREATE TABLE IF NOT EXISTS notes (id INTEGER PRIMARY KEY, channel TEXT, user TEXT, body TEXT, tag TEXT)",
"CREATE TABLE IF NOT EXISTS alert (id INTEGER PRIMARY KEY, channel TEXT, user TEXT, uri TEXT , status TEXT, tag TEXT)",
}
for _, create := range creates {
statement, er := db.Prepare(create)
Catcher(er)
statement.Exec()
//create_statement.Commit()
}
create_statement, er := db.Prepare(idea_table)
Catcher(er)
create_statement.Exec()
//create_statement.Commit()
return db
}
func filterMessages(m string) string {
db := dbInit("chatbot.sqlite")
var InspiringIdea = regexp.MustCompile("[iI]nspire [iI].*$")
var inspiringQuote = regexp.MustCompile("InspireQ.*$")
var evalTest = regexp.MustCompile("\\> test")
var checkJenkins = regexp.MustCompile("CheckJenkins.*$")
var inspiringTrivia = regexp.MustCompile("InspireT.*$")
var newTODO = regexp.MustCompile(" TODO: ")
var botCheck = regexp.MustCompile("ping$")
var reply string
switch {
case InspiringIdea.MatchString(m):
reply = randomIdea(db)
log.Println(reply)
case inspiringQuote.MatchString(m):
reply = randomQuote(db)
log.Println("replied to request for quotation")
case inspiringTrivia.MatchString(m):
log.Println("Wanted to reply to Trivia, but not implemented yet")
case newTODO.MatchString(m):
addTODO(m, db)
log.Println("Added TODO")
case evalTest.MatchString(m):
log.Printf("hit")
reply = "success"
case checkJenkins.MatchString(m):
reply = hitJenkins(os.Getenv("JENKINS_URI"))
case botCheck.MatchString(m):
reply = "pong"
log.Println("ready")
default:
log.Println("none")
}
db.Close() // TODO move
return reply
}
func addTODO(message string, dbConn *sql.DB) string {
var addQuery = "INSERT INTO notes (body) VALUES (?)"
var quote string
err := dbConn.QueryRow(addQuery).Scan(&quote)
Catcher(err)
return quote
}
func randomQuote(dbConn *sql.DB) string {
var randomQuery = "SELECT body,author FROM inspiring_quotes ORDER BY random() LIMIT 1"
var quote string
err := dbConn.QueryRow(randomQuery).Scan(&quote)
Catcher(err)
return quote
}
func inspiringTrivia() {
}
func hitJenkins(uri string) string {
log.Println("check status of jenkins job here")
return "ok"
}
func newTODO(dbConn *sql.DB, message string) string {
var randomQuery = "INSERT body,author FROM inspiring_quotes ORDER BY random() LIMIT 1"
var quote string
err := dbConn.QueryRow(randomQuery).Scan(&quote)
Catcher(err)
return quote
}
func newHandler(w http.ResponseWriter, r *http.Request) {
buf := new(bytes.Buffer)
buf.ReadFrom(r.Body)
body := buf.String()
log.Printf(body)
eventsAPIEvent, e := slackevents.ParseEvent(json.RawMessage(body), slackevents.OptionVerifyToken(&slackevents.TokenComparator{os.Getenv("TOKEN")}))
if e != nil {
log.Println(e)
w.WriteHeader(http.StatusInternalServerError)
}
if eventsAPIEvent.Type == slackevents.URLVerification {
var r *slackevents.ChallengeResponse
err := json.Unmarshal([]byte(body), &r)
if err != nil {
log.Println(e)
w.WriteHeader(http.StatusInternalServerError)
}
w.Header().Set("Content-Type", "text")
w.Write([]byte(r.Challenge))
} else if eventsAPIEvent.Type == slackevents.CallbackEvent {
innerEvent := eventsAPIEvent.InnerEvent
switch ev := innerEvent.Data.(type) {
case *slackevents.AppMentionEvent:
log.Printf("running filter on %s", ev.Text)
reply := filterMessages(ev.Text)
if reply != "none" {
log.Printf("replied to a message match of: %s", reply)
sApi.PostMessage(ev.Channel, slack.MsgOptionText(reply, false))
} else {
mem := new(runtime.MemStats)
runtime.ReadMemStats(mem)
log.Println("health check: ready")
sApi.PostMessage(ev.Channel, slack.MsgOptionText("status: ready, health: ", false))
}
/* case *slackevents.MessageEvent:
reply := filterMessages(ev.Text)
if *reply != "none" {
log.Printf("replied to a message match of: %s", reply)
sApi.PostMessage(ev.Channel, slack.MsgOptionText(*reply, false))
*/
}
}
}
func mainHandler(w http.ResponseWriter, r *http.Request) {
}
func main() {
mux := http.NewServeMux()
mux.HandleFunc("/", mainHandler)
mux.HandleFunc("/new", newHandler)
log.Fatal(http.ListenAndServe(":5000", mux))
}
func randomIdea(dbConn *sql.DB) string {
var randomQuery = "SELECT body FROM inspiring_ideas ORDER BY random() LIMIT 1"
var idea string
err := dbConn.QueryRow(randomQuery).Scan(&idea)
log.Printf("queried rows", idea)
Catcher(err)
return idea
}
func SlackBot(dbconn *sql.DB) *slack.Client {
//user := os.Getenv("USER")
secret := os.Getenv("SECRET")
sapi := slack.New(secret)
users, err := sapi.GetUsers()
Catcher(err)
for _, u := range users {
log.Printf("creating cache %s", u.Name)
up := slack.GetConversationsForUserParameters{UserID: u.ID, ExcludeArchived: false}
// discard cursor for now
chs, _, serr := sapi.GetConversationsForUser(&up)
if serr != nil {
var cacheSQL = "REPLACE INTO cache (id INTEGER PRIMARY KEY, channel TEXT, userid TEXT ) values( (SELECT id FROM cache WHERE ch=? and userid=? ), ?,?,?,?,?,?,?) "
for _, ch := range chs {
if c, err := dbconn.Prepare(cacheSQL); err != nil {
c.Exec(ch.GroupConversation.Conversation.ID, u.ID)
}
}
}
}
return sapi
}
/*
func (sapi *slack.Client) send(mesg string) {
schannel, timestamp, err := sapi.PostMessage("kondor6c", mesg)
if err != nil {
log.Printf("%s [Error]: %s\n", timestamp, err)
return
}
log.Printf("sent message: %s\n", schannel)
}
*/
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment