mirror of
https://github.com/arnaucube/goCaptcha.git
synced 2026-02-06 19:16:44 +01:00
implemented: generate captcha and captcha solution, returns only captcha which has only fake image names and captchaid, stores also translator fake image name to real. Implemented read images dataset, storing in categories (folders names). GetImage reads fake image name, and translates to real image name, and serves the image content as fake image name
This commit is contained in:
67
captcha.go
Normal file
67
captcha.go
Normal file
@@ -0,0 +1,67 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"math/rand"
|
||||
"os/exec"
|
||||
"strings"
|
||||
)
|
||||
|
||||
type Captcha struct {
|
||||
Id string `json:"id"`
|
||||
Imgs []string `json:"imgs"`
|
||||
Question string `json:"question"`
|
||||
Date string `json:"date"`
|
||||
}
|
||||
type CaptchaSolution struct {
|
||||
Id string `json:"id"`
|
||||
Imgs []string `json:"imgs"`
|
||||
ImgsSolution []string `json:"imgssolution"`
|
||||
Question string `json:"question"`
|
||||
Date string `json:"date"`
|
||||
}
|
||||
type ImgFakePath struct {
|
||||
CaptchaId string `json:"captchaid"`
|
||||
Real string `json:"real"`
|
||||
Fake string `json:"fake"`
|
||||
}
|
||||
|
||||
func generateUUID() string {
|
||||
out, err := exec.Command("uuidgen").Output()
|
||||
check(err)
|
||||
uuid := string(out)
|
||||
uuid = strings.Replace(uuid, "\n", "", -1)
|
||||
return uuid
|
||||
}
|
||||
func generateRandInt(min int, max int) int {
|
||||
//rand.Seed(time.Now().UTC().UnixNano())
|
||||
return rand.Intn(max-min) + min
|
||||
}
|
||||
func generateCaptcha(count int) Captcha {
|
||||
var captcha Captcha
|
||||
var captchaSol CaptchaSolution
|
||||
|
||||
captcha.Id = generateUUID()
|
||||
captchaSol.Id = captcha.Id
|
||||
|
||||
for i := 0; i < count; i++ {
|
||||
nCateg := generateRandInt(0, len(categDataset))
|
||||
nImg := generateRandInt(0, len(dataset[categDataset[nCateg]]))
|
||||
//imgFakePath
|
||||
var imgFakePath ImgFakePath
|
||||
imgFakePath.CaptchaId = captcha.Id
|
||||
imgFakePath.Real = categDataset[nCateg] + "/" + dataset[categDataset[nCateg]][nImg]
|
||||
imgFakePath.Fake = generateUUID() + ".png"
|
||||
err := imgFakePathCollection.Insert(imgFakePath)
|
||||
check(err)
|
||||
captcha.Imgs = append(captcha.Imgs, imgFakePath.Fake)
|
||||
captchaSol.Imgs = append(captchaSol.Imgs, dataset[categDataset[nCateg]][nImg])
|
||||
captchaSol.ImgsSolution = append(captchaSol.ImgsSolution, categDataset[nCateg])
|
||||
}
|
||||
captcha.Question = "Select all leopards"
|
||||
captchaSol.Question = "Select all leopards"
|
||||
err := captchaCollection.Insert(captcha)
|
||||
check(err)
|
||||
err = captchaSolutionCollection.Insert(captchaSol)
|
||||
check(err)
|
||||
return captcha
|
||||
}
|
||||
@@ -2,14 +2,27 @@ package main
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"fmt"
|
||||
"image"
|
||||
"image/jpeg"
|
||||
"image/png"
|
||||
)
|
||||
|
||||
func dataToPNG(data []byte, imageName string) (image.Image, error) {
|
||||
func dataToImage(data []byte, imageExtension string) (image.Image, error) {
|
||||
reader := bytes.NewReader(data)
|
||||
img, err := png.Decode(reader)
|
||||
//img, err := png.Decode(reader)
|
||||
var img image.Image
|
||||
var err error
|
||||
switch imageExtension {
|
||||
case "png":
|
||||
img, err = png.Decode(reader)
|
||||
case "jpg", "jpeg":
|
||||
img, err = jpeg.Decode(reader)
|
||||
default:
|
||||
img = nil
|
||||
}
|
||||
if err != nil {
|
||||
fmt.Println(err)
|
||||
return img, err
|
||||
}
|
||||
return img, err
|
||||
|
||||
17
main.go
17
main.go
@@ -2,7 +2,10 @@ package main
|
||||
|
||||
import (
|
||||
"log"
|
||||
"math/rand"
|
||||
"net/http"
|
||||
"strconv"
|
||||
"time"
|
||||
|
||||
"github.com/gorilla/handlers"
|
||||
)
|
||||
@@ -10,11 +13,25 @@ import (
|
||||
func main() {
|
||||
savelog()
|
||||
log.Println("goCaptcha started")
|
||||
rand.Seed(time.Now().UTC().UnixNano())
|
||||
|
||||
//connect with mongodb
|
||||
readMongodbConfig("./mongodbConfig.json")
|
||||
session, err := getSession()
|
||||
check(err)
|
||||
captchaCollection = getCollection(session, "captchas")
|
||||
captchaSolutionCollection = getCollection(session, "captchassolutions")
|
||||
imgFakePathCollection = getCollection(session, "imgfakepath")
|
||||
|
||||
//start the server
|
||||
//http server start
|
||||
readServerConfig("./serverConfig.json")
|
||||
|
||||
//read the filenames of the dataset
|
||||
readDataset(serverConfig.ImgsFolder)
|
||||
log.Println("dataset read")
|
||||
log.Println("num of dataset categories: " + strconv.Itoa(len(dataset)))
|
||||
|
||||
log.Println("server running")
|
||||
log.Print("port: ")
|
||||
log.Println(serverConfig.ServerPort)
|
||||
|
||||
51
mongoConfig.go
Normal file
51
mongoConfig.go
Normal file
@@ -0,0 +1,51 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"io/ioutil"
|
||||
|
||||
mgo "gopkg.in/mgo.v2"
|
||||
)
|
||||
|
||||
//MongoConfig stores the configuration of mongodb to connect
|
||||
type MongoConfig struct {
|
||||
Ip string `json:"ip"`
|
||||
Database string `json:"database"`
|
||||
}
|
||||
|
||||
var mongoConfig MongoConfig
|
||||
|
||||
var captchaCollection *mgo.Collection
|
||||
var captchaSolutionCollection *mgo.Collection
|
||||
var imgFakePathCollection *mgo.Collection
|
||||
|
||||
func readMongodbConfig(path string) {
|
||||
file, e := ioutil.ReadFile(path)
|
||||
if e != nil {
|
||||
fmt.Println("error:", e)
|
||||
}
|
||||
content := string(file)
|
||||
json.Unmarshal([]byte(content), &mongoConfig)
|
||||
}
|
||||
|
||||
func getSession() (*mgo.Session, error) {
|
||||
session, err := mgo.Dial("mongodb://" + mongoConfig.Ip)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
//defer session.Close()
|
||||
|
||||
// Optional. Switch the session to a monotonic behavior.
|
||||
session.SetMode(mgo.Monotonic, true)
|
||||
|
||||
// Optional. Switch the session to a monotonic behavior.
|
||||
session.SetMode(mgo.Monotonic, true)
|
||||
|
||||
return session, err
|
||||
}
|
||||
func getCollection(session *mgo.Session, collection string) *mgo.Collection {
|
||||
|
||||
c := session.DB(mongoConfig.Database).C(collection)
|
||||
return c
|
||||
}
|
||||
4
mongodbConfig.json
Normal file
4
mongodbConfig.json
Normal file
@@ -0,0 +1,4 @@
|
||||
{
|
||||
"ip": "127.0.0.1",
|
||||
"database": "goCaptcha"
|
||||
}
|
||||
21
readDataset.go
Normal file
21
readDataset.go
Normal file
@@ -0,0 +1,21 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"io/ioutil"
|
||||
)
|
||||
|
||||
var dataset map[string][]string
|
||||
var categDataset []string
|
||||
|
||||
func readDataset(path string) {
|
||||
dataset = make(map[string][]string)
|
||||
|
||||
folders, _ := ioutil.ReadDir(path)
|
||||
for _, folder := range folders {
|
||||
categDataset = append(categDataset, folder.Name())
|
||||
folderFiles, _ := ioutil.ReadDir(path + "/" + folder.Name())
|
||||
for _, file := range folderFiles {
|
||||
dataset[folder.Name()] = append(dataset[folder.Name()], file.Name())
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -6,6 +6,9 @@ import (
|
||||
"image/jpeg"
|
||||
"io/ioutil"
|
||||
"net/http"
|
||||
"strings"
|
||||
|
||||
"gopkg.in/mgo.v2/bson"
|
||||
|
||||
"github.com/gorilla/mux"
|
||||
)
|
||||
@@ -43,12 +46,20 @@ func GetImage(w http.ResponseWriter, r *http.Request) {
|
||||
vars := mux.Vars(r)
|
||||
imageName := vars["imageName"]
|
||||
|
||||
file, err := ioutil.ReadFile(serverConfig.ImgsFolder + "/" + imageName)
|
||||
imgFakePath := ImgFakePath{}
|
||||
err := imgFakePathCollection.Find(bson.M{"fake": imageName}).One(&imgFakePath)
|
||||
check(err)
|
||||
|
||||
fmt.Println(serverConfig.ImgsFolder + "/" + imgFakePath.Real)
|
||||
|
||||
file, err := ioutil.ReadFile(serverConfig.ImgsFolder + "/" + imgFakePath.Real)
|
||||
if err != nil {
|
||||
fmt.Fprintln(w, err)
|
||||
}
|
||||
|
||||
img, err := dataToPNG(file, imageName)
|
||||
pathSplited := strings.Split(imgFakePath.Real, ".")
|
||||
imageExtension := pathSplited[len(pathSplited)-1]
|
||||
img, err := dataToImage(file, imageExtension)
|
||||
|
||||
if err != nil {
|
||||
fmt.Fprintln(w, "image "+imageName+" does not exist in server")
|
||||
@@ -58,7 +69,7 @@ func GetImage(w http.ResponseWriter, r *http.Request) {
|
||||
}
|
||||
func GetCaptcha(w http.ResponseWriter, r *http.Request) {
|
||||
|
||||
resp := ""
|
||||
resp := generateCaptcha(6)
|
||||
jsonResp, err := json.Marshal(resp)
|
||||
check(err)
|
||||
fmt.Fprintln(w, string(jsonResp))
|
||||
|
||||
Reference in New Issue
Block a user